2016-03-16 11 views
1

是否应该明确标记为虚拟全部覆盖任何级别的后代类?是否应该声明在所有级别的继承或仅在祖先级别虚拟的函数?

class Base { 
// ... 
protected: 
    virtual void to_be_derived() const; // First level to introduce this virtual function 
}; 

class LevelOne : public Base { 
// ... 
protected: 
// virtual?? 
void to_be_derived() const; 
}; 

class LevelTwo : public levelOne { 
// ... 
protected: 
// virtual?? 
void to_be_derived() const; 
}; 

我没有看到Prefixing virtual keyword to overridden methods它回答我的问题。特别是,其中的一个答案已更新,以反映与C++ 11相关的当前使用情况,特别是我不知道的override关键字!

编辑:我宁愿接受来自链接问题的后C++ 11代码的另一个答案。

+1

在dervied类中默认是虚拟的,所以添加虚拟后缀与否,函数将是虚拟的 – jonezq

+0

请注意,即使使用'override' /'final'的(正确)答案已经出现在上面的问题中。 –

+0

@jonezq我知道这个函数仍然是虚拟的,但我将它看作是向*类用户显式传达它是虚拟的。 –

回答

9

现在,最好将它们标记为override。它告诉读者该函数是虚拟的,并且也是一个故障安全机制(如果你的签名是错误的)。

我只使用virtual如果这符合已经存在的代码。

class LevelOne : public Base { 
protected: 
    void to_be_derived() const override; 
    //       | 
    // clearly virtual, certain it's the same signature as the base class 
}; 
+0

我不知道有关“覆盖”关键字的方式。感谢您的关注! –

+0

需要说明的是,第一次出现'to_be_derived'仍然需要'virtual'而没有'override'关键字? –

+0

@greendiod是的。 –

-2

基类Virtual将强制继承类,即LevelOne覆盖它。

除非您需要LevelTwo来覆盖LevelOne的实现,否则不需要将其标记为虚拟。

一般来说,除非派生类重写它,无需使用虚拟

+0

“除非需要LevelTwo来覆盖LevelOne的实现,否则不需要将其标记为虚拟。” ??? – jonezq

+1

基类virtual不会强制继承类重载它。另外,如果函数在基类中是虚拟的,那么你不需要在中间派生类中声明它是虚拟的,以便覆盖大部分派生类。 – user2079303

-1

这是更好的将其标记为虚拟和覆盖。虚拟会阻止您为交付的对象调用错误的函数。重写将防止您在签名中出错,并使代码更具可读性。如Scott Meyers在有效的C++书中写的,你不应该在delevired类中重新定义非虚函数。

+0

虚拟*如何防止您调用错误的函数*? – user2079303

+0

我的意思是说,如果有人在LevelOne和LevelTwo类中声明to_be_derived()非虚函数,并写出类似LevelOne * p1 = new LewelTwo的东西; P1-> to_be_derived();错误的功能将被调用。 –

+1

您不能在LevelOne中声明be_derived是非虚拟的,因为它在Base中是虚拟的。 – user2079303

相关问题