【问题标题】:Overriding a base class function with different return types用不同的返回类型覆盖基类函数
【发布时间】:2013-10-06 13:19:26
【问题描述】:

我有一个名为变量的基类:

class Variable
{
protected:
    std::string name;   
public:
    Variable(std::string name="");
    Variable (const Variable& other);
    virtual ~Variable(){};
};

我有几个派生类,例如 Int、Bool、String 等。例如:

class Bool: public Variable{
private:
    bool value;

public:
    Bool(std::string name, bool num);
    ~Bool();
    Bool (const Bool& other);
    bool getVal();

每个派生类都有一个名为 getVal() 的方法,该方法返回不同的类型(bool、int 等)。我想允许变量类的多态行为。
我试过:void getVal(); 这似乎是错误的,编译器显示错误:shadows Variable::getVal() 这听起来很糟糕。 我想过使用template <typename T> T getVal();,但没有帮助。

有什么建议吗?我必须为此使用强制转换吗?

非常感谢...

【问题讨论】:

  • 显示您在基类和派生类中尝试的内容
  • Variable condition = condition_statement.evaluate(type); //condition_statement.evaluate(type) 返回一个 Bool 对象 cout << condition.getval(); 编译器说:“‘类变量’没有名为‘getVal’的成员”
  • 请注意,您只能拥有 协变返回类型,而覆盖函数,否则您最终会隐藏基类函数,这不是您想要的行为。
  • cout 应该如何知道要打印什么类型?
  • 这只是一个例子...condition.getVal() 应该返回布尔值。但它也可以是字符串、int 或 folat。这取决于对象的类型。 Bool 的 getVal() 返回 bool,Int 的 getVal() 返回 int 等。我希望能够在类变量中创建方法 getVal(),该方法将被派生类的 getVal() 覆盖。

标签: c++ templates inheritance


【解决方案1】:

can't overload by return type。我认为模板在您的情况下会更好。这里不需要多态或继承:

template<class T>
class Variable {
protected:
    T value;
    std::string name;   
public:
    Variable(std::string n, T v);
    Variable (const Variable& other);
    virtual ~Variable(){};
    T getVal();
};

用法是pretty simple:

Variable<bool> condition("Name", true);
Variable<char> character("Name2", 'T');
Variable<unsigned> integer("Name3", 123);
std::cout << condition.getVal() << '\n';
std::cout << character.getVal() << '\n';
std::cout << integer.getVal() << '\n';

【讨论】:

  • 谢谢。但我需要不同的派生类(例如 Bool、String、Int、Float 等)具有不同的运算符重载行为。假设我需要 Int 覆盖 operator+ 并最终添加值,但如果尝试 Bool+Bool ,则 Bool 应该抛出异常。如何使用模板做到这一点?
  • @Shakedk,这不是问题。只需使用template specialization
  • 看起来有点复杂,但我会试一试。谢谢!
【解决方案2】:

类型在编译时确定。因此,再多的多态性也不允许您更改返回类型。
虚拟调度是在运行时完成的,但方法和对象的类型必须正确,并且在编译时必须相同。

如果只需要打印值,只需添加虚拟 ToString() 方法即可。如果您不想为每个派生类型再次编写它,甚至可以将 i 模板化。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-02-16
    • 1970-01-01
    • 1970-01-01
    • 2012-07-24
    • 1970-01-01
    相关资源
    最近更新 更多