MST

星途 面试题库

面试题:C++继承体系中成员初始化顺序及影响

考虑以下C++代码:class Base { int baseVar; public: Base(int b) : baseVar(b) { } }; class Derived : public Base { int derivedVar; public: Derived(int b, int d) : derivedVar(d), Base(derivedVar + b) { } }; 分析整个对象初始化过程中成员变量的初始化顺序,这种初始化方式可能带来什么潜在问题?如何改进以确保正确初始化?
18.0万 热度难度
编程语言C++

知识考点

AI 面试

面试题答案

一键面试

成员变量初始化顺序

  1. 父类成员变量:在Derived类对象初始化时,首先调用Base类的构造函数。在Base类构造函数执行前,Base类的成员变量baseVar会被初始化。这里Base类构造函数中baseVar使用derivedVar + b进行初始化,然而此时derivedVar尚未初始化。
  2. 子类成员变量:在Base类构造完成后,才会初始化Derived类的成员变量derivedVar

潜在问题

由于Base类构造函数中使用了尚未初始化的derivedVar来初始化baseVar,这会导致未定义行为。因为derivedVarBase类构造函数执行时其值是不确定的,可能是垃圾值,从而导致baseVar被初始化为一个错误的值。

改进方法

  1. 调整参数顺序:修改Derived类构造函数参数顺序,使得derivedVar相关计算所需的值在Base类构造函数调用前已确定。例如:
class Base { 
    int baseVar; 
public: 
    Base(int b) : baseVar(b) { } 
}; 

class Derived : public Base { 
    int derivedVar; 
public: 
    Derived(int d, int b) : derivedVar(d), Base(d + b) { } 
}; 
  1. 使用临时变量:先计算出baseVar所需的值,再传递给Base类构造函数。
class Base { 
    int baseVar; 
public: 
    Base(int b) : baseVar(b) { } 
}; 

class Derived : public Base { 
    int derivedVar; 
public: 
    Derived(int b, int d) : derivedVar(d) { 
        int temp = derivedVar + b;
        Base(temp); 
    } 
}; 

这样能确保baseVar在初始化时使用的是已确定的值,避免未定义行为。