From: PGK on
Hi all,

Why is it that an object can be initialised by itself without error?
What is the purpose of such leniency? For example:

Foo a(a); // No compile error

Cheers,

The output of the subsequent code is:

Out 1: 7
In 1 : -1149044056
In 2 : -1149044056
Out 2: 7

--------------------------------------

#include <iostream>

struct Foo {
Foo(int x) { m_x = x; }
Foo(Foo &f) { m_x = f.m_x; }
int m_x;
};

int main(int argc, char *argv[])
{
Foo a(7);
std::cout << "Out 1: " << a.m_x << std::endl;
{
Foo a(a);
std::cout << "In 1 : " << a.m_x << std::endl;
Foo b(b);
std::cout << "In 2 : " << a.m_x << std::endl;
}
std::cout << "Out 2: " << a.m_x << std::endl;

return 0;
}


--
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

From: Seungbeom Kim on
On 2010-08-02 15:01, PGK wrote:
>
> Why is it that an object can be initialised by itself without error?
> What is the purpose of such leniency? For example:
>
> Foo a(a); // No compile error

It's just that the point of declaration for a name is immediately after
its complete declarator and before its initializer (if any) [3.3.1], so
in this case the new name 'a' being declared in the inner scope is in
scope before the initializer '(a)' and hides 'a' in the outer scope.

It's not very common that this is useful, but it can be sometimes,
especially when the constructor takes pointer or reference arguments:

struct node { node* ptr; /* ... */ };
node n = { &n, /* ... */ }; // n.ptr points to n (self-pointing)

Interestingly and confusingly enough, [3.3.1] also gives examples
which seem contradictory at first:

const int i = 2;
{ int i[i]; } // declares a local of two integers

const int x = 12;
{ enum { x = x }; } // x is initialized with 12

--
Seungbeom Kim

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

From: Francesco S. Carta on
PGK <graham.keir(a)gmail.com>, on 02/08/2010 22:01:14, wrote:

> Hi all,
>
> Why is it that an object can be initialised by itself without error?
> What is the purpose of such leniency? For example:
>
> Foo a(a); // No compile error
>

I don't really know the rationale, and I'd like to understand the complete behavior too.

Seems that these instances pass through a double-step initialization, and pointers seem to be special in this regard because the first step of this initialization sets them to 0, here are some examples:

Example 1: this is a message where this feature has been utilized to initialize a singleton (see the last part of James Kanze's message in particular):

http://groups.google.com/group/comp.lang.c++/msg/c5707d36e886fe3e

Example 2: more or less as it happens here for the global int*:

//-------
#include <iostream>

using namespace std;

struct Self {
int data;

Self() : data(0) {
cout << "Self()" << endl;
}

Self(const Self& s) : data(s.data) {
cout << "Self(const Self&)" << endl;
}

Self(int data) : data(data) {
cout << "Self(int)" << endl;
}
};


int* get_pi();

int* pi = get_pi();

int* get_pi() {
if(!pi) {
cout << "initializing pi" << endl;
pi = new int;
*pi = 42;
}
return pi;
}

int main() {

Self a;
// prints Self()

Self b(b);
// prints Self(const Self&)

Self c(c.data);
// prints Self(int)

cout << a.data << endl;
// prints 0

cout << b.data << endl;
// prints some junk data

cout << c.data << endl;
// prints some other junk data

cout << *pi << endl;
// prints 42

}
//-------

--
FSC - http://userscripts.org/scripts/show/59948
http://fscode.altervista.org - http://sardinias.com

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

 | 
Pages: 1
Prev: Available C++ Libraries FAQ
Next: Foo a(a); // ?