考虑一下代码
struct X {
X (int n) {...}
};
struct Base {
Base(X & x) {...}
};
struct Derived : public Base {
Derived() : Base(x), x(2) {}
X x;
};
代码有效,我认为没有问题,但我关注: Base(x), x(2)
语句的外观。首先将实例传递给Base
,然后 初始化实际对象。这是表达意图的唯一方式吗?
答案 0 :(得分:2)
诀窍是从另一个基类派生出来,他的职责是拥有X
。
请注意,基类声明顺序很重要:
struct X {
X (int n) {}
};
struct Base {
Base(X & x) {}
};
struct OwnsAnX {
OwnsAnX(int n) : x_(n) {}
X& get_x() { return x_; }
private:
X x_;
};
struct Derived
: OwnsAnX // note: order is important
, Base
{
Derived()
: OwnsAnX(2)
, Base(get_x())
{}
// x is accessed through the inherited get_x()
};
但如果你不保持你继承的课程的正确顺序,那就容易出错
这是OP的有效关注点。解决方案是启用编译器警告-Wreorder
。
反转基类的顺序然后产生:
<source>: In constructor 'Derived::Derived()':
<source>:24:23: warning: base 'OwnsAnX' will be initialized after [-Wreorder]
, Base(get_x())
^
<source>:24:23: warning: base 'Base' [-Wreorder]
<source>:22:9: warning: when initialized here [-Wreorder]
Derived()
^~~~~~~