uninitializing constructor

D

david

Hello,

I'd like to know whether the compiler can detect a member variable which is
not initialized (on purpose) by the constructor.

Easier with an simple example (the class is supposed to be a fixed point
variable):

class A
{
private:
int my_value;
A (int init) { my_value = init; }
public:
A () {}
A (const A& init) { my_value = init.my_value; }
A& operator = (int scalar) { my_value = scalar << 8; }
...
};

int main (void)
{
int p, q;
A x, y;

p = q;
y = x;
}

The compiler complains about q beeing used but not initialized,
is there a way for it to complain about x too ?

(yes I could put 0 in the constructor, but code size is critical in the
embedded environment I use, and I'm curious too :)

If of any interest for the answer, I'm using gnu-g++. Before I post to the
gnu newsgroup, I'd like to know if the answer is part of some c++ standards.

(I also tried "A () const {}" but it is refused)

Thanks for any information,

david
 
T

Thomas Tutone

david said:
I'd like to know whether the compiler can detect a member variable which is
not initialized (on purpose) by the constructor.

Not in an implementation-independent way.

Easier with an simple example (the class is supposed to be a fixed point
variable):

class A
{
private:
int my_value;
A (int init) { my_value = init; }
public:
A () {}
A (const A& init) { my_value = init.my_value; }
A& operator = (int scalar) { my_value = scalar << 8; }
...
};

int main (void)
{
int p, q;
A x, y;

p = q;
y = x;
}

The compiler complains about q beeing used but not initialized,
is there a way for it to complain about x too ?

(yes I could put 0 in the constructor, but code size is critical in the
embedded environment I use, and I'm curious too :)

If of any interest for the answer, I'm using gnu-g++. Before I post to the
gnu newsgroup, I'd like to know if the answer is part of some c++ standards.

It's not. There is nothing in the Standard that requires a diagnostic,
so it is completely implementation dependent.

Best regards,

Tom
 
D

david

I'd like to know whether the compiler can detect a member variable which is
not initialized (on purpose) by the constructor.

Not in an implementation-independent way.
[...]
If of any interest for the answer, I'm using gnu-g++. Before I post to the
gnu newsgroup, I'd like to know if the answer is part of some c++ standards.

It's not. There is nothing in the Standard that requires a diagnostic,
so it is completely implementation dependent.

Thanks a lot,

david
 
S

Salt_Peter

david said:
Hello,

I'd like to know whether the compiler can detect a member variable which is
not initialized (on purpose) by the constructor.

yes it can, but you'ld have to code that in. For the record, thats not
needed.
rule# 1: always, always intialize your members.
The members get allocated whether you initialize them or not.
Easier with an simple example (the class is supposed to be a fixed point
variable):

class A
{
private:
int my_value;
A (int init) { my_value = init; }
public:
A () {}
A (const A& init) { my_value = init.my_value; }
A& operator = (int scalar) { my_value = scalar << 8; }

shouldn't the assignment op here be a conversion ctor instead?
...
};

int main (void)
{
int p, q;
A x, y;

p = q;
y = x;
}

The compiler complains about q beeing used but not initialized,
is there a way for it to complain about x too ?

The compiler is not required to complain about a user-type's members
that are not initialized.
(yes I could put 0 in the constructor, but code size is critical in the
embedded environment I use, and I'm curious too :)

What makes you beleive that the allocation will not take place if you
don't initialize the member variable? The members of an instance are
allocated whether you initialize them or not. Therefore the cost of
initializing the member to 0 or whatever is minimal.
If of any interest for the answer, I'm using gnu-g++. Before I post to the
gnu newsgroup, I'd like to know if the answer is part of some c++ standards.

(I also tried "A () const {}" but it is refused)

Your class should use the int list and i'm ignoring the reasons for
scalar << 8 other than state that should be a conversion ctor.
As tested in main(),
A b;
A d = b;
is not an assignment - its a copy.
A c = 10;
is not an assignment - its a conversion.

class A
{
int nvalue;
public:
A() : nvalue(0) { } // def ctor
A(int scalar) : nvalue(scalar << 8) { } // conversion ctor
A(const A& copy) { nvalue = copy.nvalue; } // copy
A& operator=(const A& rhv) // assignment
{
if (this == &rhv) return *this;
nvalue = rhv.nvalue;
return *this;
}
};

int main()
{
A a; // def ctor, nvalue = 0
A b(1); // conversion, nvalue = 256
A c = 10; // conversion!!!, nvalue = 2560;
c = b; // assignment, c.nvalue = 256
A d = b; // copy!!!!, d.nvalue = 256
return 0;
}

Perhaps i'm barking up the wrong tree.
 
M

mlimber

david said:
Hello,

I'd like to know whether the compiler can detect a member variable which is
not initialized (on purpose) by the constructor.

Easier with an simple example (the class is supposed to be a fixed point
variable):

class A
{
private:
int my_value;
A (int init) { my_value = init; }
public:
A () {}
A (const A& init) { my_value = init.my_value; }
A& operator = (int scalar) { my_value = scalar << 8; }
...
};

int main (void)
{
int p, q;
A x, y;

p = q;
y = x;
}

The compiler complains about q beeing used but not initialized,
is there a way for it to complain about x too ?

(yes I could put 0 in the constructor, but code size is critical in the
embedded environment I use, and I'm curious too :)

Thomas answered your question, but let me suggest that neither you nor
almost anyone knows enough about the language, the particular
compiler/optimizer, and the particular target systems to correctly
guess what will generate more code at this fine-grained level. But this
is not a bad thing. High-level languages exist to allow you to focus on
the high-level program, not the low-level details of your machine. On
the other hand, optimizers are usually quite good at figuring out what
will produce the smallest code (or the fastest code, depending on your
compiler switches), and you should use them to that end until
measurement -- not programmer intuition! -- tells you that you should
hand-optimize (probably in assembly).

Several examples:

1. You should generally use initialization rather than assignment when
possible. Your code above calls the constructor for x and y and then
calls the assignment operator for y, whereas it really only needed to
call the constructor for x and the copy constructor for y if you were
to declare and initialize y at the same point:

A y = x; // Or A y(x);

Maybe the optimizer will inline or get rid of the extra call, but maybe
not.

2. Initialization lists generally give better code for similar reasons.
In your trivial example above, it may not matter, but it certainly does
matter in lots of real circumstances
(http://www.parashift.com/c++-faq-lite/ctors.html#faq-10.6).

3. You have private data in your class, which, according to the
standard, the compiler is free to move around and, much to your
chagrin, pad (sometimes that is fully or partially controllable by
compiler switches and/or #pragmas).

Anyway, the point is that you are probably prematurely optimizing (cf.
the section titled "Beware Premature Optimization" in
http://www.gotw.ca/publications/mill09.htm).

Cheers! --M
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,770
Messages
2,569,586
Members
45,096
Latest member
ThurmanCre

Latest Threads

Top