类设计:将派生类添加到遗留继承层次结构中

Posted

技术标签:

【中文标题】类设计:将派生类添加到遗留继承层次结构中【英文标题】:class design: add derived class to a legacy inheritance hierarchy 【发布时间】:2016-03-31 08:45:19 【问题描述】:

说我有

Class Base

    public void foo() //a public interface to user
    
        doA();
        doB();
    
    protected void doA()... //common implementation
    protected void doB() //type specific implementation

Class Derived1 extends Base

    int a,b,c,d,e,f,g; //bulky, clumsy implementation details specific to Derived1
    @Override
    protected void doB()... //implementation for Derived1

Class Derived2 extends Base

    @Override
    protected void doB()... //a different implementation for Derived2

如果我错了,请纠正我,这是首选:

Class Derived1 extends Base

    int a,b,c,d,e,f,g; //bulky, clumsy implementation details specific to Derived1
    @Override
    protected void doA()... //move the common implementation to Derived1
    @Override
    protected void doB()... //implementation for Derived1

Class Derived2 extends Derived1

    @Override
    protected void doB()... //a different implementation for Derived2

因为后者将 Derived1 的内部暴露给 Derived2。

我的问题是,假设 Derived1 和 Base 来自现有的继承层次结构,并且 Derived1 已经覆盖了 doA() 和 doB()。在不更改旧代码的情况下添加新的 Derived2 的最佳方法是什么?

由于 Derived2 与 Derived1 具有相同的 doA() 实现,因此我不得不接受次等的第二个选项。我考虑过组合并将 Derived1 作为 Derived2 的成员,但 doA() 受到保护,因此我们无法从 Derived2 访问它。

非常感谢您的回复!

【问题讨论】:

【参考方案1】:

首先,我认为您的问题有一个错误:方法doAdoB 被声明为private。子类无法访问其父类的私有方法,并且不可能覆盖方法。

在您的示例中,如果您调用Derived1.foo(),则只会调用Base.doA()

您应该将它们声明为protected以允许方法覆盖。

在这种情况下,我认为第二个选项是可以接受的,但这取决于实际代码。

Class Base

    public void foo() //a public interface to user
    
        doA();
        doB();
    
    protected void doA()... //common implementation
    protected void doB() //type specific implementation

Class Derived1 extends Base

    @Override
    protected void doB()... //implementation for Derived1

Class Derived2 extends Base

    @Override
    protected void doB()... //a different implementation for Derived2

【讨论】:

感谢指出,这是一个错误。我的观点是,Derived2 必须继承 Derived1 的“庞大、笨拙的实现细节”似乎是不祥之兆。

以上是关于类设计:将派生类添加到遗留继承层次结构中的主要内容,如果未能解决你的问题,请参考以下文章

C++中派生类的构造函数怎么显式调用基类构造函数?

C ++继承:具有基类类型的虚函数中派生类类型的参数

C ++中派生类的相等性测试[重复]

C#中派生类调用基类构造函数用法分析

C++ 命名空间中派生类中的 Qt 样式表(选择器)

虚拟继承中派生类的大小