2009-08-20 52 views
1

为什么我不能在B类初始化列表中访问基类A的成员?从C++中导出问题

class A 
    { 
    public: 
     explicit A(int a1):a(a1) 
     { 
     } 
     explicit A() 
     { 
     } 

    public: 
     int a; 

    public: 
     virtual int GetA() 
     { 
      return a; 
     } 
    }; 

    class B : public A 
    { 
    public: 
     explicit B(int a1):a(a1) // wrong!, I have to write a = a1 in {}. or use A(a1) 
     { 
     } 
     int GetA() 
     { 
      return a+1; 
     } 
    }; 

    class C : public A 
    { 
    public: 
     explicit C(int a1):a(a1) 
     { 
     } 
     int GetA() 
     { 
      return a-1; 
     } 
    }; 
+0

我已经改变了措辞,使问题更加具体:您不能从初始化列表中访问字段,而您确实可以从构造函数体中访问它。 – 2009-08-21 06:40:16

回答

6

A的构造函数之前B的运行,并且,或明或暗地,前者构造A的所有实例,其中包括a成员。因此B不能在a上使用构造函数,因为该字段已经构建。你试图使用的表示法正好表示要在a上使用构造函数,并且在那一点上它是不可能的。

6

要建立在亚历克斯通过控制其建设的回答,您可以初始化基类的‘一’成员,像这样:

class B : public A 
{ 
public: 
    explicit B(int a1) : A(a1) { } // This initializes your inherited "a" 
    ... 
}; 

请注意,我构建的基类(资本“A”),而不是尝试直接初始化其继承成员(小写“a”,从您的示例中绘制)。

+0

非常感谢,pilcrow :) – user25749 2009-08-20 08:39:48

0

为了进一步巩固段落符号的答案,你可以很容易地通过在B级覆盖它初始化是你想要的成员:

class B : public A 
{ 
public: 
    int a; // override a 

    explicit B(int a1) : a(a1) // works now 
    { 
    } 

    ... 
}; 

虽然,我不一定会推荐这一点;)

+0

哈!新徽章:“巴别塔”,用于延伸本身已经扩展的答案。 :) – pilcrow 2009-08-20 04:47:58