Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Mike Lewis on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

constructor question

Status
Not open for further replies.

mcswew

Programmer
Nov 20, 2002
8
0
0
IE
Hi,
I am looking at some code that has a class called sample that has as a private member an instance of class digitalSample called digData.
the code for the sample default constructor is

sample::sample():digData(0){...contents etc .....}

I read this as the sample default constructor explicitly calling the digData general constructor.

My question is why is the code written this way??? Why not simply write

sample::sample{ digData(0)}

that is putting the digData contructor call in the body of the sample constructor.
Is it just convention or is it to ensure digData constructor gets called first???


 
I would assume that you cant. The reason being is the class has been initialized and digData does not have a default constructor. By putting it in the initialization list, you initialize the class digData.

Matt
 
Hi Matt,
I just found out that digData is not a class but a pointer of type short.
The code in a local.h file is
typedef short int16;
typedef int16 digSample

sample.h then declares the class sample as
class sample {
public:
digSample* digData; etc....}

and finally sample.cpp has

sample ::sample() : digData(0) {....etc....
}

So digData(0) seems to be a way of initialising this pointer to 0 or Null. But why do it this way??? Why not simply use digData = 0;
I know its not a big deal but I'd like to know why its done this way or if in fact it is initialising the poiter to 0.
thanks
Will
 
Yes its initialising the pointer to NULL (or 0). Why ? I dont know, i can only speculate .....

In my humble opinion i ve always thought it is a different way of doing the same thing :

class CMyClass : public CAnotherClass
{
CMyClass();
// ...
};

CMyClass::CMyClass():CAnotherClass(Parameters)
{
}

and

CMyClass::CMyClass()
{
CAnotherClass::CAnotherClass(Parameters);
}

Appear to do the same thing.

having said that, i personally use the first method because it looks neater (unless there are too many things to initialise and then it looks plain messy!! )

Regards,
Rich.
 
Thanks Rich! I appreciate your insight.
Will
 
mcswew

The constructor is using an initialization list. This method must be used for nonstatic constant data members and also for reference data members as they both can only be initialized when they are created. Any other use of the initialization list is just a matter of coding style. Hope this sheds some light. [spin]

If you choose to battle wits with the witless be prepared to lose.

[cheers]
 
Pete,

I apologize - i forgot to put Parameters in the constructor argument list.

But I did test it, and yes it does compile and run.

heres what i did :

class CAnotherClass
{
public:
CAnotherClass () {}
CAnotherClass (char *Parameters)
{
MessageBox(NULL,Parameters,"",0);
}

};

class CMyClass : public CAnotherClass
{
public:
CMyClass (char *Parameters)
{
CAnotherClass ::CAnotherClass (Parameters);
}

};

int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
CMyClass *C = new CMyClass ("Rich");

return 0;
}

give it a go. im using vc6.

Regards,
Richard.
 
Code:
CMyClass::CMyClass():CAnotherClass(Parameters) 
{
}

and

CMyClass::CMyClass()
{
    CAnotherClass::CAnotherClass(Parameters);
}

[red]Appear to do the same thing.[/red]


Alright i was wrong. You can call the constructor of the base class. [machinegun] ...(pete)

Could have sworn that was illegal outside the initialization list!

However they are not the same and the second example, while it compiles, is still wrong.

Code:
class foo{
protected:
	int _n;
public:
	foo():_n(0){}
	foo(int n): _n(n){}
	virtual ~foo(){}
};
class wrong : public foo{
public:
	wrong(int n){
		foo::foo(n);
		cout << &quot;wrong.n: &quot; << _n << endl;
	}
};
class bar : public foo{
public:
	bar(int n):foo(n){
		cout << &quot;bar.n: &quot; << _n << endl;
	}
};

int _tmain(int argc, _TCHAR* argv[])
{
	wrong w(12);
	bar b(10); 
	return 0;
}


-pete
 
Pete,

In fact you are right - you cant do that - in fact you can if you want - but it's not initialisation.

wrong(int n){
>> foo::foo(n);
cout << &quot;wrong.n: &quot; << _n << endl;
}

What is happening is it is creating an instance of foo with n and then destroying it (because it goes out of scope on the same line).

given that - my modified example proves the point.
class CAnotherClass
{
public:
CAnotherClass () {
memset(cName,0,20);
}

~CAnotherClass() { MessageBox(NULL,&quot;Destructor&quot;,&quot;&quot;,0); };

CAnotherClass (char *Parameters)
{
MessageBox(NULL,Parameters,&quot;&quot;,0);
strcpy(cName,Parameters);
}

char cName[20];
};

class CMyClass : public CAnotherClass
{
public:
CMyClass (char *Parameters)
{
CAnotherClass ::CAnotherClass (Parameters);
}

};

int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
CMyClass *C = new CMyClass (&quot;Rich&quot;);

MessageBox(NULL,C->cName,&quot;&quot;,0);

return 0;
}


so mcswew - i apologise for posting misleading information. I was wrong there.

But i hope that answers your question ! ! !

Regards,
Richard.
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top