c++ 如何使用自定义模板子类创建初始化列表构造函数?

tp5buhyn  于 2023-08-09  发布在  其他
关注(0)|答案(2)|浏览(109)

基本上,我想做的是能够使用像这样的原语列表来构造一个对象:

int main()
{
  // C primitives initialization list
  int matrix[2][2] = { { 1, 2 }, { 2, 3 }, };

  // C++ stl class initialization list
  std::string s = { 'f', 'o', 'o' '\0' };

  // My custom 2x2 Matrix subclass
  Matrix2<int> mat = { { 2, 0 }, { 6, 7 } }; // is it possible?
}

字符串
我试过使用这个帖子中的声明,但是没有成功
第一个月

template <class T, unsigned int M, unsigned int N> class Matrix {
  
  // Matrix(initializer_list<T> &&lst) : _First(nullptr), _Last(nullptr) {} // (1) Does not work
  Matrix(std::initializer_list<T> &&lst) { } // (2) no error on definition itself

}

template <class T> class Matrix2 : public SquareMatrix<T, 2> {};

**(1):**由于以上clang错误,无法工作:clang: Member initializer '_First' does not name a non-static data member or base class [mem_init_not_member_or_class]
**(2):**也不工作,因为MatrixMatrix2构造时出错:

  • clang: Too few template arguments for class template 'Matrix' [template_arg_list_different_arity]
  • clang: No viable conversion from 'int' to 'Matrix<int, 2, 2>' [typecheck_nonviable_condition]

为了简化问题,我省略了主要代码full code can be found here

6za6bjd0

6za6bjd01#

您可以将其编码为std::initializer_list<std::initializer_list<T>>

template<typename T>
class Matrix2
{
public:
    Matrix2(std::initializer_list<std::initializer_list<T>> list) {
        if (list.size() > 2)
            throw std::out_of_range{ "Too many rows." };

        int rowNum = 0;
        for (auto& row : list)
        {
            if(row.size() > 2)
                throw std::out_of_range{ "Too many cols." };

            int colNum = 0;
            for (auto& ele : row)
                mat[rowNum][colNum++] = ele;
            rowNum++;
        }
        // for debug
        for (int i = 0; i < 2; i++)
            for (int j = 0; j < 2; j++)
                std::cout << mat[i][j];
    }
private:
    T mat[2][2];
};

int main()
{
    Matrix2 mat{ {1, 2}, {3, 4} };
    return 0;
}

字符串

bmvo0sr5

bmvo0sr52#

{..}没有类型,它不是std::initializer_list
{..}禁止除std::initializer_list和C数组类型以外的大多数演绎。
std::initializer_list最多用于“未知”大小。
对于matrix 2x2,C-array似乎更合适(大小可能在编译时检查):

template <typename T>
class Matrix2
{
public:
    Matrix2(const T (&ini)[2][2]) : mat{ini[0][0], ini[0][1], ini[1][0], ini[1][1]} {}
// ...
private:
    T mat[2][2];
};

字符串

相关问题