C++ 将固定长度的括号内初始值设定项列表传递给函数
我希望能够将括号内的初始值设定项列表传递给我的类的构造函数,它表示一个固定维度的矩阵。这是我的代码:C++ 将固定长度的括号内初始值设定项列表传递给函数,c++,arrays,aggregate-initialization,C++,Arrays,Aggregate Initialization,我希望能够将括号内的初始值设定项列表传递给我的类的构造函数,它表示一个固定维度的矩阵。这是我的代码: #包括 #包括 模板 使用array2d=std::array; 模板 类矩阵{ 私人: array2d值; 公众: 矩阵(常量数组2d和值):值(值){} }; int main(){ 矩阵mat1({ {1, 2, 3}, {4, 5, 6} }); } 我的假设是,array2d是从我作为参数传递给构造函数的初始值设定项列表自动创建的,但情况似乎并非如此,因为编译器抛出以下错误: 170
#包括
#包括
模板
使用array2d=std::array;
模板
类矩阵{
私人:
array2d值;
公众:
矩阵(常量数组2d和值):值(值){}
};
int main(){
矩阵mat1({
{1, 2, 3},
{4, 5, 6}
});
}
我的假设是,array2d
是从我作为参数传递给构造函数的初始值设定项列表自动创建的,但情况似乎并非如此,因为编译器抛出以下错误:
1704186652/source.cpp:16:23: error: no matching constructor for initialization of 'Matrix<double, 2, 3>'
Matrix<double, 2, 3> mat1 ({
^ ~
1704186652/source.cpp:8:7: note: candidate constructor (the implicit copy constructor) not viable: cannot convert initializer list argument to 'const Matrix<double, 2, 3>'
class Matrix {
^
1704186652/source.cpp:8:7: note: candidate constructor (the implicit move constructor) not viable: cannot convert initializer list argument to 'Matrix<double, 2, 3>'
class Matrix {
^
1704186652/source.cpp:12:3: note: candidate constructor not viable: cannot convert initializer list argument to 'const array2d<double, 2UL, 3UL>' (aka 'const std::__1::array<std::__1::array<double, 2>, 3>')
Matrix(const array2d<T, N, M>& value) : value(value) {}
^
1704186652/source.cpp:16:23:错误:没有用于初始化“矩阵”的匹配构造函数
矩阵mat1({
^ ~
1704186652/source.cpp:8:7:注意:候选构造函数(隐式副本构造函数)不可行:无法将初始值设定项列表参数转换为“常量矩阵”
类矩阵{
^
1704186652/source.cpp:8:7:注意:候选构造函数(隐式移动构造函数)不可行:无法将初始值设定项列表参数转换为“矩阵”
类矩阵{
^
1704186652/source.cpp:12:3:注意:候选构造函数不可行:无法将初始值设定项列表参数转换为“const-array2d”(也称为“const-std::_1::array”)
矩阵(常量数组2d和值):值(值){}
^
首先,您的维度颠倒了
Matrix<double, 2, 3>
矩阵
如果展开模板,这将成为
std::array<std::array<double, 2>, 3>
std::数组
或者是一个三元素数组,每个元素有两个值,而不是一个两元素数组,每个元素有三个值
带有嵌套构造函数和参数的大括号初始化列表有时可能是一个破译挑战,通常你只需在编译前随机戳和涂鸦。以下是使用gcc 10.2编译的,并使用调试器检查所有内容是否都在其应有的位置。我解释大括号的最佳尝试:
#include <cstddef>
#include <array>
template <typename T, size_t N, size_t M>
using array2d = std::array<std::array<T, N>, M>;
template <typename T, size_t N, size_t M>
class Matrix {
private:
array2d<T, N, M> value;
public:
Matrix(const array2d<T, N, M>& value) : value(value) {}
};
int main() {
Matrix<double, 2, 3> mat1({ // Initializing the 1st constructor parameter
{ // std::array< ,3> using initializer_list constructor
// Initializing std::array<T, 2>s
{1, 2},
{3, 4},
{5, 6}
},
});
return 0;
}
#包括
#包括
模板
使用array2d=std::array;
模板
类矩阵{
私人:
array2d值;
公众:
矩阵(常量数组2d和值):值(值){}
};
int main(){
矩阵mat1({//初始化第一个构造函数参数
{//std::array<,3>使用初始值设定项\u list构造函数
//初始化std::数组
{1, 2},
{3, 4},
{5, 6}
},
});
返回0;
}
我个人建议使用@SamVarshavchik的解决方案。但是如果您想保存一对{}
,可以执行以下操作:
#include <iostream>
#include <cstddef>
#include <array>
template <typename T, size_t N, size_t M>
using array2d = std::array<std::array<T, N>, M>;
template <typename T, size_t N, size_t M>
class Matrix {
private:
array2d<T, N, M> value;
public:
Matrix(const array2d<T, N, M>& value) : value(value) {
std::cout << "using array2d" << std::endl;}
Matrix(std::initializer_list<std::array<double,N>> values) {
// Assign values to this->value
std::cout << "using initializer list" << std::endl;
}
};
int main() {
array2d<double, 2, 3> values;
Matrix<double, 2, 3> mat0(values);
Matrix<double, 2, 3> mat1({{1, 2},{3, 4},{5, 6}});
Matrix<double, 2, 3> mat2({{1, 2},{3, 4},{5, 6},{7,8}}); // > 3 rows but compiles
//Matrix<double, 2, 4> mat3({{{1, 2},{3, 4},{5, 6}}}); // <- ambiguous. Note the extra "{}"
return 0;
}
将列表的值分配给您的this->value
,这是一个家庭作业
请注意,您可以向初始值设定项列表中添加比矩阵中的行更多的行。使用此解决方案时,您应该提供运行时检查。因此,我更喜欢@SamVarshavchik的解决方案,编译器会在那里告诉您错误所在。但为什么要实现矩阵的自定义版本?有很多库可以为您做这件事。@TheOldJonny因为这是家庭作业,我想正确的答案应该是保持矩阵的结构,而是使用array2d=std::array;将array2d中的类型参数N和M交换到
。好吧,如果这是您的初衷,那么这将是100%保证的,毫无疑问是正确的。
using array2d
using initializer list