C++ 无法从初始值设定项\u列表转换为my类型,该类型具有模板可变构造函数
所以,这不是我真正要做的事,我只是在玩玩。我为任何数字类型和任意坐标数的向量编写了一个C++ 无法从初始值设定项\u列表转换为my类型,该类型具有模板可变构造函数,c++,templates,c++17,variadic-templates,initializer-list,C++,Templates,C++17,Variadic Templates,Initializer List,所以,这不是我真正要做的事,我只是在玩玩。我为任何数字类型和任意坐标数的向量编写了一个Vector类。它用作向量。代码如下: #include <array> #include <functional> namespace World { template <typename NumType, unsigned char Size> class Vector { public: using CoordType = NumType; templa
Vector
类。它用作向量
。代码如下:
#include <array>
#include <functional>
namespace World {
template <typename NumType, unsigned char Size>
class Vector
{
public:
using CoordType = NumType;
template<typename... NumTypes>
constexpr Vector(NumTypes&&... vals) : values{ std::forward<NumTypes>(vals)... }
{
static_assert(sizeof...(NumTypes) == Size, "You must provide N arguments.");
}
Vector(const std::array<NumType, Size>& values) : values(values) {}
Vector(const std::array<NumType, Size>&& values) : values(std::move(values)) {}
const NumType& operator[](size_t offset) const { return values[offset]; }
NumType& operator[](size_t offset) { return values[offset]; }
//! Converts all values to new given type
template <typename NewType>
constexpr Vector<NewType, Size> Convert() const { return Convert<NewType>(std::make_index_sequence<Size>{}); }
//! Converts all values via the conversion function
template <typename NewType>
Vector<NewType, Size> Convert(const std::function<NewType(NumType)>& callback) const { return Convert<NewType>(std::make_index_sequence<Size>{}, callback); }
std::array<NumType, Size> values;
private:
//! Converts all values to new given type
template <typename NewType, std::size_t ... Is>
constexpr Vector<NewType, Size> Convert(std::index_sequence<Is...>) const { return { { static_cast<NewType>(values[Is])}... }; }
//! Converts all values via the conversion function
template <typename NewType, std::size_t ... Is>
Vector<NewType, Size> Convert(std::index_sequence<Is...>, const std::function<NewType(NumType)>& callback) const { return { { callback(values[Is])}... } ; }
};
#包括
#包括
名称空间世界{
模板
类向量
{
公众:
使用CoordType=NumType;
模板
constexpr向量(NumTypes&…vals):值{std::forward(vals)…}
{
static_assert(sizeof…(NumTypes)=Size,“必须提供N个参数”);
}
向量(const std::数组和值):值(值){}
向量(const std::array&&values):值(std::move(values)){
const NumType&运算符[](size_t offset)const{返回值[offset];}
NumType和运算符[](大小偏移){返回值[offset];}
//!将所有值转换为新的给定类型
模板
constexpr Vector Convert()const{return Convert(std::make_index_sequence{});}
//!通过转换函数转换所有值
模板
向量转换(const std::function&callback)const{return Convert(std::make_index_sequence{},callback);}
std::数组值;
私人:
//!将所有值转换为新的给定类型
模板
constexpr向量转换(std::index_序列)const{return{{static_cast(values[Is])}…};}
//!通过转换函数转换所有值
模板
向量转换(std::index_序列,const std::function&callback)const{return{{callback(values[Is])}…};}
};
现在我要做的是确保上面声明的转换函数正常工作。用法如下:
using namespace World;
using Vector3D = Vector<double, 3>;
using Vector3Int = Vector<int, 3>;
#include <cmath>
int main()
{
const Vector3D src{ 1.4, 2.5, 3.6 };
const Vector3Int target = src.Convert<int>([](double val) { return (int)std::round(val); });
return 0;
}
使用名称空间世界;
使用Vector3D=矢量;
使用Vector3Int=Vector;
#包括
int main()
{
常量向量3d src{1.4,2.5,3.6};
const Vector3Int target=src.Convert([](双val){return(int)std::round(val);});
返回0;
}
这里的问题是,当编译转换函数时,生成的新值以std::initializer\u list
的形式出现。出于某种原因,这不符合构造函数向量(NumTypes&&…vals)的条件
。现在我不希望有初始值设定项列表构造函数-预期参数的数量不是可变的,它必须是大小
模板参数所说的任何值
那么如何解决这个问题呢?我如何将std::initializer\u list
转换成NumTypes&&…vals
是什么
我必须承认,我不知道我在做什么,我正在努力提高我的C++知识。
< > >代码>转换<代码>,你有参数包<代码> < /COD>,你想使用它与<代码>回调< /代码>和<代码>值< /> > < < 参数包扩展“扩展为零个或多个模式的逗号分隔列表”,因此,当与问题中的值一起使用时,您将得到以下结果:是…
0, 1, 2
值[Is]…
=>值[0]、值[1]、值[2]
1.4, 2.5, 3.6
1, 3, 4
回调(值[Is])…
=>回调(值[0])、回调(值[1])、回调(值[2])
您希望创建一个大括号的init列表,如下所示:
{callback(values[0]), callback(values[1]), callback(values[2])}
// =>
{1, 3, 4}
因此:
模板
矢量
转换(标准::索引_序列,
const std::函数和回调)const
{
返回{callback(值[Is])…};
}
我没有仔细查看它,但是Convert
函数是否应该像这样返回:返回{callback(values[Is])…};
?OT:首先,常量右值引用没有意义(特别是,如果您以后试图“移动”它们)第二,基本类型的完美转发也没有意义。对于int
或double
@tedlynmo这样的类型,复制和移动没有区别。你真是个天才!但是点的位置是基于其他代码的,当它们位于括号后面时,它们会起作用……你可以发布一个ans吗这解释了{{x..}}
和{{x}..}
之间的区别吗?@TomášZato(简化:返回{callback(值[Is])…};
也应该有效).我写不出答案。一个3小时的会议现在开始。我将把它交给其他人。:-@TomášZato,我看到没有人捡到球,所以我尝试用例子来解释。我觉得我自己解释得不好,所以我希望其他人能给出更好的答案(或者在我的答案上改进,如果可以补救的话)
template <typename NewType, std::size_t... Is>
Vector<NewType, Size>
Convert(std::index_sequence<Is...>,
const std::function<NewType(NumType)>& callback) const
{
return {callback(values[Is])...};
}