我有一个Vector
类和一个Matrix
类。我想使用 =
运算符将 Vector
类隐式转换为 Matrix
类。这些类的定义如下所示。
template <unsigned int dim>
class Vector {
public:
std::array<double, dim> x;
};
template <unsigned int nrow, unsigned int ncol>
class Matrix {
public:
std::array<Vector<ncol>, nrow> x;
auto& operator=(Vector<ncol> v)
{
x.fill(v);
return *this;
}
};
int main()
{
Vector<2> vec1;
vec1.x[0] = 1;
vec1.x[1] = 2;
Matrix<1, 2> mat1;
mat1 = vec1;
std::cout << mat1.x[0].x[0] << std::endl;
std::cout << mat1.x[0].x[1] << std::endl;
}
这一切正常。但是,我想介绍另一个 operator=
,它应该如下所示工作。
auto& operator=(Vector<nrow> v)
{
for(unsigned int row=0; row < nrow; ++row){
x[row].x[0] = v[row];
}
return *this;
}
但是,由于重载实例化为相同的签名(对于 nrow=ncol
的情况),我不确定如何设计这样的方法。具体来说,我想知道是否可以仅在 nrow!=ncol
的情况下定义第二种方法。
我尝试通过定义两种类型来使用 std::enable_if
using nrow_t = std::integral_constant<unsigned int,nrow>;
using ncol_t = std::integral_constant<unsigned int,ncol>;
然后使用 std::is_same
,但我不确定如何进一步进行。
最佳答案
在这种情况下,使用命名函数可能会容易得多。它将准确传达正在发生的事情,不会让任何人感到惊讶。那就是说你可以使用这样的东西
template <unsigned int nrow, unsigned int ncol>
class Matrix {
public:
std::array<Vector<ncol>, nrow> x;
template<unsigned int cols,
std::enable_if_t<cols == ncol || (cols == ncol && ncol == nrow)>* = nullptr>
auto& operator=(Vector<cols> v)
{
x.fill(v);
return *this;
}
template<unsigned int rows,
std::enable_if_t<rows == nrow && nrow != ncol>* = nullptr>
auto& operator=(Vector<rows> v)
{
for(unsigned int row=0; row < nrow; ++row){
x[row].x[0] = v[row];
}
return *this;
}
};
对于第一个重载,我们enable_if
when cols == ncol || (cols == ncol && ncol == nrow)
为真。当它具有正确数量时会发生这种情况,因为列或行和列相同并且它具有正确数量的列。第二个重载使用 rows == nrow && nrow != ncol
并且仅在行和列不相同且行数量匹配时才会激活。
关于c++ - 不同非类型模板参数的不同成员函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44502738/