[C++]协变返回类型
我有一个 VectorN
类和一个从 VectorN
继承的 Vector3
类(例如,它可以处理叉积)。我无法确定不同运算符的返回类型。示例:
class VectorN
{
public:
VectorN(){};
virtual VectorN operator*(const double& d) {.....};
std::vector<double> coords;
};
class Vector3 : public VectorN
{
public:
Vector3(){};
virtual Vector3 operator*(const double& d) {....};
};
此特定示例产生 C2555 错误:
“Vector3::operator *”:重写虚函数返回类型与“VectorN::operator *”不同且不协变,请参阅“VectorN::operator *”的声明。
问题是我没有返回对 Vector3
的引用,并且 Vector3
类在 operator*
的声明中没有完全定义代码>.但是,我希望我的 operator*
是虚拟的,并且当我将 Vector3
与常量相乘时,我希望返回 Vector3
(否则,如果我这样做 (Vector3*double).crossProduct(Vector3)
,它将返回错误)。
我能做些什么 ?
谢谢!
I have a VectorN
class, and a Vector3
class inherited from VectorN
(which can handle cross products for example). I have trouble determining the return types of the different operators. Example:
class VectorN
{
public:
VectorN(){};
virtual VectorN operator*(const double& d) {.....};
std::vector<double> coords;
};
class Vector3 : public VectorN
{
public:
Vector3(){};
virtual Vector3 operator*(const double& d) {....};
};
This particular example produces a C2555 error:
'Vector3::operator *': overriding virtual function return type differs and is not covariant from 'VectorN::operator *', see declaration of 'VectorN::operator *'.
The problem is that I don't return a reference to a Vector3
, and that the Vector3
class is not fully defined at the declaration of the operator*
. However, I want my operator*
to be virtual, and I want to return a Vector3
when I multiply a Vector3
with a constant (otherwise, if I do (Vector3*double).crossProduct(Vector3)
, it would return an error).
What can I do ?
Thanks!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
你需要重新设计。首先,优先选择自由函数而不是成员函数。您应该拥有的唯一成员函数是需要访问私有函数的函数。
从这个组合开始:
这里协方差工作得很好,因为类型是引用或指针,并且您可以重用代码。 (
static_cast
是免费的、性能明智且安全的,因为您知道派生类型。)然后您实现您的自由函数:
对
Vector3
执行相同的操作。我们所做的是,您可以通过一种简单的方式来编写这些运算符,因为您可以使用运算符的核心,并且由于协方差,返回类型是匹配的。
但请注意警告,您可能不需要任何警告。您想要进行的扩展可以通过在
vector
或valarray
上运行的自由函数来实现。You need a re-design. First, prefer free-functions over member-functions. The only member functions you should have are the ones that need access to privates.
Start with this combo:
Here covariance works fine because the type is a reference or pointer, and you re-use code. (
static_cast
is free, performance-wise, and safe since you know the derived type.)Then you implement your free-functions:
Do the same with
Vector3
.What's been done is you get an easy way to write these operators because you get to use the core of the operator, and the return type matches, thanks to covariance.
Do heed warnings though, you probably don't need any of it. And extensions you want to make can be made via free-functions operating on a
vector
orvalarray
.我能想到的最好的方法是用智能指针替换返回类型,并放弃协方差以支持多态性:
我建议这样做的原因是您正在使用虚拟函数,因此无论如何都不需要知道对象的确切类型。
根本问题是调用者需要为按值返回的对象分配存储空间。该存储不能动态变化,因此您不可避免地会陷入在堆上分配对象的困境。
The best I can think of is to replace the return type with a smart pointer and forgo covariance in favor of polymorphism:
The reason I suggest this is that you are using virtual functions, so knowing the exact type of the object isn't necessary anyway.
The underlying problem is that the caller needs to allocate storage for an object returned by value. That storage cannot vary dynamically, so you are inevitably stuck allocating the object on the heap.