试图了解使用虚拟基类继承的影响,尤其是在运行时成本方面。我想到的情况还涉及接口(interface)(或ABC)。
I----------
/ | \ |
D1 D2 D3 Isub
| /
D3Dec
因此,我们有一个接口(interface)
I
,我们有不同的实现D1
,D2
和D3
。但现在的问题是,有一个特殊的装饰器,它仅包装了一些(任意)I
实现,然后根据通过I
表示的协定添加了扩展功能。因此,从逻辑或设计的 Angular 来看,希望通过从
Isub
派生的子接口(interface)I
来表达这种扩展能力。因此,任何Isub
也会自动履行I
契约(Contract)。问题:性能影响
现在,要在C++中实现这种功能,必须完成
I
接口(interface)virtual
的任何实现,并且类似地,Isub
必须从virtual
继承I
,否则我们最终将在I
中驻留两个D3Dec
子对象。I
的每个实现都必须通过棘手的虚拟基本偏移调整来付出内存布局方面的代价。正确? I
和Isub
都是纯虚拟的,即没有成员而只有纯虚函数时,Isub
的引用时。如果客户端调用扩展功能,则他们实际上会在D3Dec
中调用该功能的实现,而这反过来又使用其他I
-functionity来实现扩展功能,因为显然D3dec
对装饰的具体I
-实现一无所知。这是否必然意味着我们必须使用虚拟继承?还是有任何基于模板的技巧来解决这个问题,但仍然有一个(抽象的)子接口(interface)Isub
? 当然,显而易见的替代方法是切断
I
和Isub
之间的链接,将其转变为琐碎的混合。这是可行的,但是很丑陋,因为Isub
独立于I
并没有多大意义。两者甚至都在签名上使用相同的数据类型,等等。 最佳答案
通过使接口(interface)类成为具体类的模板参数,可以完全避免菱形继承(钻石问题)问题。这样就不再需要虚拟类继承。
class I { ... };
template<class Ifc>
class D3Impl : public Ifc
{ ... };
typedef D3Impl<I> D3;
class Isub : public I { ... };
class D3Dec : public D3Impl<Isub>
{ ... };
关于c++ - 从接口(interface)进行虚拟继承的成本,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/47722508/