I've a question about initialization of inherited members in constructor of derived class. Example code:
class A
{
public:
int m_int;
};
class B: public A
{
public:
B():m_int(0){}
};
This code gives me the following output:
In constructor 'B::B()':
Line 10: error: class 'B' does not have any field named 'm_int'
(see http://codepad.org/tn1weFFP)
I'm guessing why this happens? m_int
should be member of B
, and parent class A
should already be initialized when initialization of m_int
in B
happens (because parent constructors run before member initialization of inherited class). Where is a mistake in my reasoning? What is really happens in this code?
EDIT
: I'm aware of other possibilities to initialize this member (base constructor or assignment in derived constructor), but I want to understand why is it illegal in the way I try it? Some specific C++ language feature or such? Please point me to a paragraph in C++ standard if possible.
You need to make a constructor for A (it can be protected so only B can call it) which initializes m_int just as you have, then you invoke :A(0)
where you have :m_int(0)
You could also just set m_int = 0
in the body of B's constructor. It is accessible (as you describe) it's just not available in the special constructor syntax.
In order to construct an instance of class B
you first instantiate an instance of class A
. During that instantiation m_int
gets initialized. It's after that intialization that b
's constructor is called, so you can't reinitialize m_int
. If that's your goal then you can implement a constructor for A
that takes an int and then call that in B
's initialization list:
class A
{
public:
A(int x): m_int(x) {}
int m_int;
};
class B: public A
{
public:
B(): A(2) {}
};
What you want is this:
class A{
public:
A() : m_int(0);
int m_int;
};
so that m_int
is initialized in the correct place.
Edit:
From a comment above, the reason the compiler complains when you try to initialize the m_int
variable in B
is that it's already been initialized by the constructor of A
. That is, you can't re-initialize something, only reassign. So, you can reassign like Ben Jackson stated above or you can initialize in the proper place.
make a constructor in A
and use B(): A(2) {}
insteed of B():m_int(0){}
its working.