operator+
我在使用非模板类之前没有问题地重载Matrix<U> Matrix<U>::operator+(const Matrix<U>&, const Matrix<U>&)
。这里我使用的是模板类。
friend
必须采用零或一个参数。
似乎编译器忽略了friend
template<typename U>
Matrix<U> operator+(const Matrix<U>& a, const Matrix<U>& b);
关键字。
我也试过
expected unqualified-id before 'template'
但是这给了我一个不同的编译器错误。
operator+
如何使用模板类重载{{1}}?
答案 0 :(得分:2)
首先,我建议改为重载+=
,然后用+
写+=
。其次,朋友通常不应该是模板。
template<typename T>
class Matrix
{
friend Matrix operator+(Matrix a, const Matrix& b) {
a += b;
return std::move(a);
}
friend Matrix& operator+=(Matrix& a, const Matrix& b) {
a.increase_by(b);
return a;
}
protected:
void increase_by( const Matrix& other );
size_t _m = 0
size_t _n = 0;
std::vector<T> _alloc;
};
template<class T>
void Matrix<T>::increase_by(const Matrix<T>& other) {
if(this->_m == other._m && this->_n == other._n) {
for (auto i = 0; i < _m*_n; ++i) {
_alloc[i] += other._alloc[i];
}
// ...
} else {
throw "Matrix dimension mismatch error";
}
}
请注意,通过高效移动,上面的内容将为您提供合理有效的a+b+c+d+e
,因为lhs会被创建一次并重复移动。
答案 1 :(得分:2)
您可以使用成员函数或非成员函数重载+运算符。
当它是一个成员函数时,运算符的LHS是调用函数的对象,运算符的RHS是函数的参数。因此,成员函数的唯一参数是RHS。
当它是一个成员函数时,运算符的LHS是函数的第一个参数,运算符的RHS是函数的第二个参数。
会员功能
template<typename T>
class Matrix
{
Matrix operator+(const Matrix& rhs) const {
...
}
};
如果要在类定义之外实现它,可以使用:
template<typename T>
Matrix<T> Matrix<T>::operator+(const Matrix& rhs) const {
...
}
非会员功能
template<typename T>
class Matrix
{
Matrix operator+(const Matrix& lhs, const Matrix& rhs) {
...
}
};
如果要在类定义之外实现它,则需要添加一些前向声明代码:
// Forward declare the class template
template <typename T> class Matrix;
// Declare the function
template <typename T> Matrix<T> operator+(const Matrix<T>& lhs, const Matrix<T>& rhs);
// Declare the friend in the class definition
template <typename T>
class Matrix
{
friend Matrix operator+<T>(const Matrix& lhs, const Matrix& rhs);
// ^^^^
// This makes operator+<int> a friend of Matrix<int>, not a friend
// of Matrix<double>
};
然后实现函数
template <typename T> Matrix<T> operator+(const Matrix<T>& lhs, const Matrix<T>& rhs)
{
...
}
通过此设置,oprator+<int>
仅是Matrix<int>
的朋友,而不是friend
的{{1}}。
如果您使用
Matrix<double>
然后,template <typename U>
friend
Matrix<U> operator+(const Matrix<U>& a, const Matrix<U>& b);
的所有实例化都是operator+
所有实例化的朋友,您不需要。
<强>更新强>
示例工作代码:
Matrix
答案 2 :(得分:0)
解决方案:不显式声明模板,它们是自动生成的。也许有人可以更详细地解释原因?
friend
Matrix operator+(const Matrix& a, const Matrix& b)
{
if(a._m == b._m && a._n == b._n)
{
Matrix ret(a._m, a._n);
return ret;
}
else
{
throw "Matrix dimension mismatch error";
}
}