gpt4 book ai didi

c++ - 多个类的父类的部分特化

转载 作者:塔克拉玛干 更新时间:2023-11-03 00:36:42 25 4
gpt4 key购买 nike

我想对模板类使用部分特化,以便该模板类的所有子类都将使用该特化。让我用一个例子来解释它:)

template < typename T, unsigned int rows, unsigned int cols>
class BaseMatrix {...};

这个类将有指定矩阵结构的子类,如稀疏、密集、对角线……

template < typename T, unsigned int rows, unsigned int cols>
class DiagonalMatrix : public BaseMatrix<T,rows,cols>{..}

然后这些类将再次有指定存储的子类:堆栈数组、 vector 、列表、队列......

template < typename T, unsigned int rows, unsigned int cols>
class StackDiagonalMatrix : public DiagonalMatrix<T, rows, cols> {..}

还有一个Matrix类,它提供了所有的数学功能。该模板类实现了operator+、operator-等...

   template <typename T, 
template<typename, unsigned, unsigned> class MatrixContainer,
unsigned Rows,
unsigned Cols>
class matrix;

对于最后一个类,我想编写这样的专业:

template <typename T,unsigned Rows, unsigned Cols>
class matrix<T, BaseMatrix, Rows, Cols> {};

template <typename T,unsigned Rows, unsigned Cols>
class matrix<T, DiagonalMatrix, Rows, Cols> {};

但是当我编写一个继承自 DiagonalMatrix 的 StackDiagonalMatrix 时,它没有找到 DiagonalMatrix 的特化——实际上它根本没有找到特化。

error: aggregate ‘matrix<int, StackDenseMatrix, 3u, 2u> matrix’ has incomplete type and cannot be defined

现在有解决这个问题的方法吗?你能为几个模板类的父类编写一个特化吗?

非常感谢!

涉及的完整源代码:

    template <typename T, unsigned int rows, unsigned int cols>
class BaseMatrix {
protected:
BaseMatrix(){};
static const unsigned rowSize = rows;
static const unsigned colSize = cols;
};

template <typename T, unsigned int rows, unsigned int cols>
class DenseMatrix : public BaseMatrix<T, rows, cols> {
protected:
DenseMatrix(){};

};

template <typename T, unsigned int rows, unsigned int cols>
class StackDenseMatrix : public DenseMatrix<T, rows, cols> {

public:
typedef T value_type;

private:
value_type grid[rows][cols];
StackDenseMatrix();
};

template<typename value_type, unsigned int rows, unsigned int cols>
StackDenseMatrix<value_type, rows,cols>::StackDenseMatrix () {
for (unsigned int i = 0; i < this->rowSize; i++) {
for (unsigned int j = 0; j < this->colSize; j++) {
grid[i][j] = 0;
}
}
}

template <typename T, template<typename, unsigned, unsigned> class MatrixContainer ,unsigned Rows, unsigned Cols>
class matrix;

template <typename T,unsigned Rows, unsigned Cols>
class matrix<T,BaseMatrix, Rows, Cols> {
matrix(){};
};

int main () {
matrix<int, StackDenseMatrix, 3, 2> matrix;
return 0;
}

最佳答案

继承不适用于模板特化。当您调用 matrix<int,StackDenseMatrix,3,2> matrix; , 它将选择 matrix 的通用模板, 因为第二个参数是 StackDenseMatrix , 不是 BaseMatrix .尽管这些类通过继承相关,但没有任何区别,它们不是完全相同的类型,因此编译器不会选择 matrix 的特化。 .

为了解决您的问题,我认为在这种情况下继承对您没有任何好处。在泛型编程中,更合适的工具是类型特征、策略和概念。在这种情况下,您应该能够应用一些类型特征来实现类似的目标。我喜欢使用的一个技巧是默认模板参数依赖于先前的模板参数,然后进行部分特化。例如如下:

enum MatrixStorage {
DenseMatrix,
SparseMatrix
};

enum MatrixStructure {
GeneralMatrix,
SquareMatrix,
DiagonalMatrix //, ...
};

template <typename T, unsigned Rows, unsigned Cols>
class StackDenseMatrix {
public:
typedef T value_type;
static const MatrixStorage Storage = DenseMatrix;
static const MatrixStructure Structure = GeneralMatrix;
//..
};

//General template with default arguments:
template <typename T,
template <typename, unsigned, unsigned> class MatrixContainer,
unsigned Rows, unsigned Cols,
MatrixStorage Storage = MatrixContainer<T,Rows,Cols>::Storage,
MatrixStructure Structure = MatrixContainer<T,Rows,Cols>::Structure>
class matrix;

//Specialization with given arguments:
template <typename T,
template <typename, unsigned, unsigned> class MatrixContainer,
unsigned Rows, unsigned Cols>
class matrix<T,MatrixContainer,Rows,Cols,DenseMatrix,GeneralMatrix> {
//implementation of matrix for when the container is dense and has general structure...
};

int main() {
matrix<int,StackDenseMatrix,3,2> M; //no extra arguments, and the right specialization will be selected based on the traits of StackDenseMatrix.
return 0;
};

我有自己的矩阵库,它严重依赖模板元编程和泛型编程技术,按照上面的例子,为不同类型的矩阵结构和存储提供矩阵运算的特殊实现,它工作得很好方法。我曾经对不同的矩阵类型使用继承,但现在我已经切换到仅依赖类型特征、概念、策略和 Sfinae 开关,这是一个更实用的解决方案。

关于c++ - 多个类的父类的部分特化,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6154844/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com