在抽象基类中重载运算符的正确方法是什么? [英] What is the proper way to overload operators in abstract base classes?

查看:226
本文介绍了在抽象基类中重载运算符的正确方法是什么?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设我有一个抽象基类,只是定义了一个可以执行添加的容器:

  class Base { 
public:
virtual〜Base(){}
virtual Base operator +(const Base& rhs)= 0;
};然后我想要Base的子类提供实际操作:







b $ b

  class Derived:public Base {
public:
基本运算符+(const Base& rhs){//不会编译
// actual implementation
}
};

这是我的问题:operator +()应该返回一个新的Base对象,它不会编译。



我试图通过使用工厂来返回对Base对象的引用,但是在操作符的主体中我发现自己在做转换,因为添加只对Derived对象有意义。



在任何情况下,感觉我都咬我自己的尾巴,是否有适当的解决方案?



UPDATE:基于到目前为止的答案,似乎我使用错误的模式。我想将接口与实现分开,这样库代码只需要知道接口和客户端代码提供的实现。我试图做到这一点,提供接口作为一个抽象基类,和实现作为子类。



UPDATE2:我的问题实际上是两个问题,一个具体的问题(关于重载抽象类中的运算符),另一个关于我的意图(如何允许客户端自定义实施)。前者已经回答:不。对于后者,似乎我使用的接口类模式实际上是一个很好的解决这个问题(根据

最好的不是。



操作符+ 返回一个值,抽象类型。



重载对称二进制运算符,例如 operator +

重载运算符只能用于具体类型,并避免继承具体类型以防止 / code>作为自由函数,你可以控制哪些类型的组合可以明智地组合,反过来防止组合的对象类型的组合是没有意义的。



如果你有一个有效的方式通过两个基类引用执行添加和创建一个新的对象,你必须通过指针,引用或指针包裹智能对象返回。因为你不能保留 + 的常规语义,我建议使用一个命名的函数,例如。 Add(),而不是使用惊讶语法创建运算符+


Suppose I have an abstract base class, that just defines a container on which addition can be performed:

class Base {
public:
    virtual ~Base() {}
    virtual Base operator+(const Base& rhs) =0;
};

Then I want subclasses of Base to provide the actual operation:

class Derived: public Base {
public:
    Base operator+(const Base& rhs) { // won't compile
        // actual implementation
    }
};

Here is my problem: operator+() is supposed to return a new Base object, but Base being abstract it won't compile.

I tried to get around that by using a factory to return a reference to a Base object, but then in the body of the operator I find myself doing casts, because the addition only makes sense on Derived objects.

In any case, it feels like I am biting my own tail, is there a proper solution to this?

UPDATE: Based on the answers so far, it seems I am using the wrong pattern. I want to separate the interface from the implementation, so that library code only has to know the interface and client code provides the implementation. I tried to do that by providing the interface as an abstract base class, and the implementation as subclasses.

UPDATE2: My question was actually 2 questions, a concrete one (about overloading operators in abstract classes) and another about my intent (how do I allow the client to customize the implementation). The former has been answered: don't. For the latter, it seems that the Interface Class pattern I use is actually a good one to solve that problem (according to Griffiths and Radford), it's just that I should not mess with overloaded operators.

解决方案

The best thing is not to.

operator+ returns a value and you can't return a value of an abstract type, by definition. Overload the operators only for concrete types and avoid inheriting from concrete types to prevent "slicing by overloaded operator".

Overload symmetric binary operators like operator+ as free functions and you can control which combinations of types can be sensibly combined, and conversely prevent the combination of objects of types for which the combination doesn't make sense.

If you have a valid way of performing an "add" via two base class references and creating a new object you will have to return via a pointer, reference or pointer-wrapping smart object. Because you can't preserve the conventional semantics of + I would recommend using a named function, e.g. Add() instead of making an operator+ with a "surprising" syntax.

这篇关于在抽象基类中重载运算符的正确方法是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆