为什么纯虚拟/抽象类需要构造函数,特别是对于受保护的const成员变量
Why does a purely virtual/abstract class require a constructor, in particular for protected const member variables?
我定义了一个纯虚拟类:
class BaseClass {
protected:
const int var;
public:
void somefun() = 0; // what I mean by a purely virtual class
// stuff...
};
如果我不添加这样定义的构造函数:
BaseClass(const int & VAR) : var(VAR) {};
我随后必须在派生类中使用,我的派生类无法将常量变量var初始化为它想要的任何值。现在我真正理解了这里发生了什么。在构造派生类之前,将调用基类的构造函数,此时必须初始化const成员变量。我的问题不是"我如何让我的代码工作"之类的问题,这已经解决了。我的问题是编译器为什么认为它是必要的。对于一个纯粹的虚拟类,难道不应该允许我写这样的东西吗:
class DerivedClass : BaseClass {
public:
DerivedClass() : var(SOME_VALUE) {};
}
如果编译器知道对基类构造函数的调用之后必然会调用某个派生类构造函数(因为抽象类型的对象永远无法实例化),这难道不应该给我们更多的余地吗?
这一切都是C++选择绕过Diamond问题的结果吗?即使是这样,编译器是否应该至少以某种方式允许纯虚拟函数的const成员变量在派生类中定义的可能性?这太复杂了吗?或者这会干扰C++对Diamond问题的解决方案吗?
谢谢大家的帮助。
它不是"纯虚拟的"(不管你的意思是什么)——它包含一个数据成员。
类成员只能由该类的构造函数的初始化器列表初始化,而不能由派生类的构造函数列表初始化。这就是指定对象初始化的方式:所有初始化的成员都在构造函数体开始之前初始化。
常量对象必须初始化,因为以后不能为它们赋值。
因此,具有常量数据成员的类必须在每个构造函数中对其进行初始化。
对于一个纯粹的虚拟课堂,难道不应该允许我写一些东西吗像
不,但你可以(在这种情况下应该)写这样的东西:
class DerivedClass : BaseClass {
public:
DerivedClass() : BaseClass(SOME_VALUE) {};
};
对象的构造按特定顺序进行。在运行派生类的构造函数之前,必须完全构造基类,这样派生构造函数才能使用完全形式且有效的基对象。如果基成员变量的初始化被推迟到派生类的构造,那么这个不变量就会被破坏。
相关文章:
- C++:无法访问声明的受保护成员
- 继承和友元函数,从基类访问受保护的成员
- 为什么派生类的好友不能使用受保护的成员?
- C++:为什么无法在派生类中访问受保护的构造函数?
- 公共/私有/受保护是否会更改内存中结构的排列?
- 在父类中公开受保护的构造函数
- 如何从其他结构访问受保护的结构变量
- 如何实现返回受保护结构的私有函数
- 相同的层次结构,访问基类的受保护成员时的行为不同
- 从模板化父类中的派生内部类访问受保护的成员变量
- 为什么继承的受保护构造函数不能公开?
- 在使用受保护和继承时无法访问在类中声明的私有成员
- C++中的受保护变量
- 在此上下文中受保护 c++
- 同一模板类但模板类型的受保护成员
- 基类中受保护的纯虚函数如何被基类的友元类使用?
- 受保护的嵌套结构不能用作派生外部类中的返回类型?
- 有没有办法通过 main 函数访问受保护的矢量大小而无需将其转换为公共?
- 跨公共/受保护访问的基于const的函数重载
- 为什么纯虚拟/抽象类需要构造函数,特别是对于受保护的const成员变量