从覆盖函数调用重写函数

时间:2009-05-13 10:04:35

标签: c++ inheritance oop virtual override

假设我在B类中有虚函数foo(),我需要在B的派生类之一D类中略有不同的行为。是否可以创建重写函数D :: foo(),并调用B: :foo()从那里经过特殊情况处理?像这样:

void D::foo()
{
  if (/*something*/)
     // do something
  else
     B::foo();
}

我不是在问这是否会奏效,我知道会这样。我想知道,对于一个好的OOD来说它是否正确。

7 个答案:

答案 0 :(得分:19)

这非常好。实际上,执行某些操作的规范方法是调用基类方法,然后执行任何操作(或者反过来)。我在这里想operator=。构造函数通常也以这种方式工作,即使在初始化列表中有点伪装。

答案 1 :(得分:6)

是的,只要你没有违反Liskov替代原则,它就完全可以了。

答案 2 :(得分:4)

是的,是的。

答案 3 :(得分:1)

我已经看到GUI框架使用它来回退基类的默认实现,其中包含用于发出错误信号/抛出异常/返回通用值的代码。

答案 4 :(得分:1)

没关系。你给出的语法也可以用来临时关闭多态,即当你调用obj-> B :: foo()方法将从B类中选择,无论foo()是否为虚拟,如果obj是实例B与否(它必须是扩展B的类的实例)。

答案 5 :(得分:0)

是的,这就是你的编译器每次生成构造函数和析构函数时为你做的事情:例如调用母亲的一个。我经常依赖自己代码中的“技巧”。

答案 6 :(得分:0)

调用base的实现很好,但是有条件地会使你与构造函数语义分开,这与其他答案中的建议相反。

您可能会以两种方式遇到fragile base class问题:

  • 假设B::foo()为整个层次结构提供了共同的行为(即,忘记方法并不总是被调用)
  • 令人讨厌的问题取决于// do something实际上做了什么!

为了完整起见,我们提一下对称设计方法:Template pattern(基本实现调用特定的子部分)