我有2个类,base(带有复制构造函数)和派生,在baseΙ有重载operator+
:
class Base {
public:
Base(const Base& x) {
// some code for copying
}
Base operator+(const Base &bignum) const {
Base x;
/* ... */
return x;
}
};
class Derived : public Base {
};
当我尝试做类似的事情时
Derived x;
Derived y;
Derived c=x+y;
我收到错误:conversion from "Base" to non-scalar type "Derived" derived
问题可能在于operator +返回Base
类型的对象,我想将它分配给Derived
类型对象吗?
答案 0 :(得分:5)
实际上你不需要重新定义org.apache.jasper.JasperException: /EjemploProfesor/Class/receiveName.jsp (line: 1, column: 1) The value for the useBean class attribute mynames.Names is invalid.
(除非你的设计需要它,正如Ajay的例子所指出的那样)。
采用以下简约示例:
operator+
这非常有效,因为遇到struct Base {
Base operator+ (Base a) const
{ cout <<"Base+Base\n"; }
Base& operator= (Base a)
{ cout<<"Base=Base\n"; }
};
struct Derived : public Base { };
int main() {
Base a,b,c;
c=a+b; // prints out "Base+Base" and "Base=Base"
Derived e,f,g;
e+f; // prints out "Base+Base" (implicit conversion);
}
时,编译器会找到基类的e+f
,并且他隐式地从operator+
转换为Derived
,并计算结果属于Base
类型。您可以轻松编写Base
。
问题始于分配到派生。只要您尝试c=e+f
,就会收到错误消息。编译器不确定如何将A放入B中。这种谨慎是有道理的:所有类人猿都是动物,但所有动物都不一定是猿猴。
如果g=e+f;
的字段多于Derived
,那就更明显了:编译器应该如何初始化它们?基本上,如何告诉编译器他将如何使用其他东西制作Base
?用构造函数!
Derived
一旦你定义了这个,一切都按照你的预期运作:
struct Derived : public Base {
Derived()=default;
Derived(const Base& a) : Base(a) { cout<<"construct B from A\n"; }
};
这是live demo。
答案 1 :(得分:2)
这不是一个正确的设计。考虑具有Point2D
和x
以及y
类的类Point3D
,该类继承自具有其他成员Point2D
的{{1}}。你跟随的事情会有所帮助吗?
z
当被称为:
Point2D operator+(const Point2D &pt) const;
答案 2 :(得分:1)
是的,这正是问题所在。 plus运算符仅保证返回Base对象,因此您可以将其分配给Base对象。所有派生对象都可以替换为Bases,但不能替代其他方式。