如何避免C类模板中的无限递归
我有一个矩阵类,其大小由模板参数决定.
template <unsigned cRows,unsigned cCols> class Matrix { ... }; 我的程序使用几种大小的矩阵,通常是2×2,3×3和4×4.通过使用模板参数而不是运行时参数设置矩阵大小,编译器可以进行大量的内联和优化. 但是现在我需要一个成员函数来返回一个新的矩阵,该矩阵的行少一列,列少一列. Matrix<cRows - 1,cCols - 1> Reduced(unsigned row,unsigned col) const { ... } 这个想法是它将返回一个删除了指定行和列的矩阵.在实践中,这将仅使用具有至少三行和三列的矩阵来调用,在最小的位置返回2×2. 编译器没有看到下限,因此它会陷入无限递归,试图以不断减小的大小实例化模板.我尝试在函数本身中放入两条线索,这些较小的尺寸不会发生: Matrix<cRows - 1,unsigned col) const { static_assert(cRows > 1 && cCols > 1); if (cRows <= 1 || cCols <= 1) throw std::domain_error(); Matrix<cRows - 1,cCols - 1> r; // ... initialize r ... return r; } static_assert和if语句似乎都不是编译器的强大线索,因为永远不会生成0x0矩阵. (具有讽刺意味的是,它确实抱怨if语句具有恒定的编译时条件.) 有没有人有任何关于如何避免这种编译时无限递归的建议? 解决方法
您需要为没有行或没有列的Matrix提供专门化.
例如. template<unsigned cRows> class Matrix< cRows,0 > { Matrix<cRows - 1,0> Reduced() { return Matrix<cRows - 1,0>(); } }; template<unsigned cCols> class Matrix< 0,cCols > { Matrix<0,cCols - 1> Reduced() { return Matrix<0,cCols - 1>(); } }; template<> class Matrix< 0,0 > { Matrix<0,0> Reduced() { return Matrix<0,0>(); } }; 您遇到的问题是尝试使用一组特定的模板参数实例化Matrix Reduced函数时,总是需要为不同的参数集(cRows – 1,cCols -1)实例化Matrix模板.这种递归必须在某处停止.如果你只处理方形矩阵,那么你可以减少专业化. 此外,如果你永远不会使用1×1矩阵,那么你可以用一个完全空的类来停止递归,这是2×2矩阵上的reduce的结果. template<> class Matrix< 1,1 > {}; (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |