C++ 派生类运算符=错误
我在编译以下代码时出错。我想基本上创建一个名为SqMatrix的派生类,square matrix,作为matrix的派生类型。但是,编译器不允许我实例化一些自定义运算符。下面是我的代码matrix.hC++ 派生类运算符=错误,c++,operator-keyword,instantiation,derived-class,C++,Operator Keyword,Instantiation,Derived Class,我在编译以下代码时出错。我想基本上创建一个名为SqMatrix的派生类,square matrix,作为matrix的派生类型。但是,编译器不允许我实例化一些自定义运算符。下面是我的代码matrix.h #ifndef matrix_h #define matrix_h #include <string> #include <vector> #include <typeinfo> template<class T> class Matrix {
#ifndef matrix_h
#define matrix_h
#include <string>
#include <vector>
#include <typeinfo>
template<class T>
class Matrix {
private:
size_t nrow;
size_t ncol;
std::string typenm;
std::vector<T> *vec;
public:
Matrix(): nrow(0), ncol(0), vec(), typenm("") {}
Matrix(size_t nr, size_t nc, T value=T()): nrow(nr), ncol(nc), typenm(std::string(typeid(T).name()))
{ vec = new std::vector<T>(nrow*ncol, value); }
~Matrix()
{ delete vec; }
size_t getnrow() const
{ return nrow; }
size_t getncol() const
{ return ncol; }
std::string gettypenm() const
{ return typenm; }
T *getdata()
{ return vec->data(); }
T *getdata() const
{ return vec->data(); }
T &at(size_t ir, size_t ic)
{ return vec->at(ic*nrow+ir); }
T &at(size_t ir, size_t ic) const
{ return vec->at(ic*nrow+ir); }
virtual void resize(size_t nr, size_t nc, T value=T())
{
vec->resize(nr*nc, value);
nrow = nr;
ncol = nc;
}
Matrix &operator =(const Matrix &mat);
Matrix operator +(const Matrix &mat) const;
Matrix operator -(const Matrix &mat) const;
};
template<class T>
class SqMatrix: public Matrix<T> {
private:
size_t ndim;
public:
SqMatrix(): Matrix<T>(), ndim(0) {}
SqMatrix(size_t nd, T value=T()): Matrix<T>(nd, nd, value), ndim(nd) {}
size_t getndim() const
{ return ndim; }
virtual void resize(size_t nd, T value=T())
{
Matrix<T>::resize(nd, nd, value);
ndim = nd;
}
SqMatrix &operator =(const SqMatrix &sqmat)
{
Matrix<T>::operator =(sqmat);
return *this;
}
};
#endif
#ifndef矩阵
#定义矩阵
#包括
#包括
#包括
模板
类矩阵{
私人:
尺寸(如图所示);
尺寸公差;
std::字符串类型nm;
std::vector*vec;
公众:
矩阵():nrow(0),ncol(0),vec(),typenm(“”{}
矩阵(大小为nr,大小为nc,t值为t()):nrow(nr),ncol(nc),typenm(std::string(typeid(t).name())
{vec=new std::vector(nrow*ncol,value);}
~Matrix()
{删除向量;}
大小\u t getnrow()常量
{返回nrow;}
大小\u t getncol()常量
{返回ncol;}
std::string gettypenm()常量
{返回类型nm;}
T*getdata()
{返回向量->数据();}
T*getdata()常量
{返回向量->数据();}
T&at(尺寸ir、尺寸ic)
{return vec->at(ic*nrow+ir);}
T&at(尺寸ir、尺寸ic)常数
{return vec->at(ic*nrow+ir);}
虚拟空间大小调整(大小\u t nr,大小\u t nc,t值=t()
{
矢量->调整大小(nr*nc,数值);
nrow=nr;
ncol=nc;
}
矩阵和运算符=(常数矩阵和矩阵);
矩阵运算符+(常数矩阵和矩阵)常数;
矩阵算子-(常数矩阵和矩阵)常数;
};
模板
类SqMatrix:公共矩阵{
私人:
尺寸(ndim);;
公众:
SqMatrix():Matrix(),ndim(0){}
SqMatrix(size_t nd,t value=t()):矩阵(nd,nd,value),ndim(nd){
大小\u t getndim()常量
{返回ndim;}
虚拟空间大小调整(大小\u t nd,t值=t())
{
矩阵::调整大小(nd,nd,值);
ndim=nd;
}
SqMatrix和运算符=(常量SqMatrix和sqmat)
{
矩阵::运算符=(sqmat);
归还*这个;
}
};
#恩迪夫
然后是我的方法实现matrix.cpp
#include <iostream>
#include <cstring>
#include <string>
#include <typeinfo>
#include "precision.h"
#include "matrix.h"
#include "lapack.h"
template<class T>
Matrix<T> &Matrix<T>::operator =(const Matrix<T> &mat)
{
try {
if(nrow != mat.nrow) throw "Matrix::operator =: Invalid mat.nrow";
if(ncol != mat.ncol) throw "Matrix::operator =: Invalid mat.ncol";
}
catch(const char *str) {
std::cout << str << std::endl;
}
memcpy(vec->data(), mat.vec->data(), sizeof(T)*nrow*ncol);
return *this;
}
template<class T>
Matrix<T> Matrix<T>::operator +(const Matrix<T> &mat) const
{
try {
if(nrow != mat.nrow) throw "Matrix::operator +: Invalid mat.nrow";
if(ncol != mat.ncol) throw "Matrix::operator +: Invalid mat.ncol";
}
catch(const char *str) {
std::cout << str << std::endl;
}
Matrix<T> matsum(nrow, ncol);
for(size_t i = 0; i < nrow*ncol; ++i)
matsum.vec->at(i) = vec->at(i) + mat.vec->at(i);
return matsum;
}
template<class T>
Matrix<T> Matrix<T>::operator -(const Matrix<T> &mat) const
{
try {
if(nrow != mat.nrow) throw "Matrix::operator -: Invalid mat.nrow";
if(ncol != mat.ncol) throw "Matrix::operator -: Invalid mat.ncol";
}
catch(const char *str) {
std::cout << str << std::endl;
}
Matrix<T> matdif(nrow, ncol);
for(size_t i = 0; i < nrow*ncol; ++i)
matdif.vec->at(i) = vec->at(i) - mat.vec->at(i);
return matdif;
}
template Matrix<dreal> &Matrix<dreal>::operator =(const Matrix<dreal> &);
template Matrix<dreal> Matrix<dreal>::operator +(const Matrix<dreal> &) const;
template Matrix<dreal> Matrix<dreal>::operator -(const Matrix<dreal> &) const;
template Matrix<dcmplx> &Matrix<dcmplx>::operator =(const Matrix<dcmplx> &);
template Matrix<dcmplx> Matrix<dcmplx>::operator +(const Matrix<dcmplx> &) const;
template Matrix<dcmplx> Matrix<dcmplx>::operator -(const Matrix<dcmplx> &) const;
#包括
#包括
#包括
#包括
#包括“precision.h”
#包括“矩阵h”
#包括“lapack.h”
模板
矩阵和矩阵::运算符=(常数矩阵和矩阵)
{
试一试{
如果(nrow!=mat.nrow)抛出“矩阵::运算符=:无效的mat.nrow”;
如果(ncol!=mat.ncol)抛出“矩阵::运算符=:无效的mat.ncol”;
}
捕获(常量字符*str){
std::cout data(),sizeof(T)*nrow*ncol);
归还*这个;
}
模板
矩阵::运算符+(常数矩阵和矩阵)常数
{
试一试{
如果(nrow!=mat.nrow)抛出“矩阵::运算符+:无效的mat.nrow”;
如果(ncol!=mat.ncol)抛出“矩阵::运算符+:无效的mat.ncol”;
}
捕获(常量字符*str){
标准::在(i)+材料向量->在(i);
回垫;
}
模板
矩阵::运算符-(常数矩阵和矩阵)常数
{
试一试{
如果(nrow!=mat.nrow)抛出“矩阵::运算符-:无效的mat.nrow”;
如果(ncol!=mat.ncol)抛出“矩阵::运算符-:无效的mat.ncol”;
}
捕获(常量字符*str){
标准::在(i)处计算-材料向量->在(i)处;
返回matdif;
}
模板矩阵&矩阵::运算符=(常量矩阵&);
模板矩阵矩阵::运算符+(常数矩阵和)常数;
模板矩阵矩阵::运算符-(常数矩阵&)常数;
模板矩阵&矩阵::运算符=(常量矩阵&);
模板矩阵矩阵::运算符+(常数矩阵和)常数;
模板矩阵矩阵::运算符-(常数矩阵&)常数;
最后是主代码test.cpp
#include <iostream>
#include <typeinfo>
#include "constants.h"
#include "matrix.h"
using namespace std;
using namespace constants;
int main()
{
const size_t Ndim(7);
SqMatrix<dreal> sqmatA(Ndim,Ndim), sqmatB(Ndim,Ndim), sqmatC(Ndim,Ndim);
for(size_t i = 0; i < Ndim; ++i)
for(size_t j = 0; j < Ndim; ++j) {
sqmatA.at(j, i) = (i+1) * (j+1);
sqmatB.at(j, i) = i + j;
}
sqmatC = sqmatA + sqmatB;
return 0;
}
#包括
#包括
#包括“constants.h”
#包括“矩阵h”
使用名称空间std;
使用名称空间常量;
int main()
{
const size_t Ndim(7);
SQMAT矩阵sqmatA(Ndim,Ndim),sqmatB(Ndim,Ndim),sqmatC(Ndim,Ndim);
对于(尺寸i=0;i
奇怪的是,编译器抱怨:
test.cpp: In function ‘int main()’:
test.cpp:20: error: no match for ‘operator=’ in ‘sqmatC = Matrix<T>::operator+(const Matrix<T>&) const [with T = double](((const Matrix<double>&)((const Matrix<double>*)(& sqmatB.SqMatrix<double>::<anonymous>))))’
matrix.h:62: note: candidates are: SqMatrix<T>& SqMatrix<T>::operator=(const SqMatrix<T>&) [with T = double]
test.cpp:在函数“int main()”中:
test.cpp:20:错误:在'sqmatC=Matrix::operator+(常数矩阵和)常数[带T=double]((常数矩阵和)((常数矩阵*)(&sqmatB.SqMatrix::)中,'运算符='不匹配'
matrix.h:62:注:候选值为:SqMatrix和SqMatrix::operator=(const SqMatrix&)[带T=double]
很明显,这是由于派生类SqMatrix的运算符=造成的。我实际上为SqMatrix实现了运算符=的,为什么它仍然抱怨,或者我犯了什么实际错误
提前谢谢
Yi在子类
SqMatrix
中缺少一个运算符+
。这就是为什么矩阵和sqmatA+sqmatB
使用泛型类矩阵的运算符+
,它返回一个矩阵
,因此不能传递给子类中特定的运算符=
lassSqMatrix
有关编译错误:
“+”运算符返回“Matrix”类的对象。您没有在“SqMatrix”中定义接受“Matrix”对象的赋值运算符
另一方面,使平方矩阵成为矩阵的子类可能是最好的主意,也可能不是:
- 您在(ndim)周围携带了一个多余的成员变量,它的维度、数据以及继承的x和y维度不是作为维度和数据的方阵
- 没有矩阵重载的方法来利用平方性
- 你可以创建一个与之平方的法线矩阵(因为它恰好具有相同的x&y维度)
正方形矩阵更适合作为矩阵的(计算)属性。你能把你的代码缩减到一个最小的例子来重现错误吗?memcpy(vec->data(),mat.vec->data(),sizeof(T)*nrow*ncol)如果T是非POD,这将不会太好。另外,如果您在矩阵类中更改为:std::vector vec;
则不需要运算符=
。要添加,请在矩阵类中使用std::vector
,而不是std::vector*
,以及所有这些赋值运算符是不必要的,包括派生类中的。您正在做编译器应该做的工作