470,815 Members | 1,324 Online
Bytes | Developer Community
New Post

Home Posts Topics Members FAQ

Post your question to a community of 470,815 developers. It's quick & easy.

Initialisation of reference vs. initialisation of reference member

1) Is this initialising the reference 'u' to the address of the literal '2'
or to the address 0x00000002?

unsigned const& u = 2;
2) What is the different between the initialisation of 'u' and 'S::u' below?

unsigned const& u = 2;

struct S
{
unsigned const& u;

S() : u (2) { }

} s;

int main(int argc, char* argv[])
{
return 0;
}
VisualStudio 2005 generates "error C2354: 'S::u' : initialization of
reference member requires a temporary variable" but does not complain about
the initialisation of 'u'. A couple of other compilers that I have say
nothing about either (GCC 3.3.4, ADS 1.2).
Any illumination will be greatly appreciated.
Tim
May 30 '06 #1
8 2938

"Tim Clacy" <no*******@nospamphaseone.nospamdk> wrote in message
news:44***********************@dread12.news.tele.d k...
1) Is this initialising the reference 'u' to the address of the literal
'2' or to the address 0x00000002?

unsigned const& u = 2;


Easy enough to find out:
std::cout << u;
outputs
2
so it would initializing the reference to be the address where the constant
unsigned int is stored.
May 30 '06 #2
Jim Langston wrote:
"Tim Clacy" <no*******@nospamphaseone.nospamdk> wrote in message
news:44***********************@dread12.news.tele.d k...
1) Is this initialising the reference 'u' to the address of the
literal '2' or to the address 0x00000002?

unsigned const& u = 2;


Easy enough to find out:
std::cout << u;
outputs
2
so it would initializing the reference to be the address where the
constant unsigned int is stored.


Hi Jim,

Thanks for replying. I think all you code proves is that the value of u is
2; it doesn't really prove that this is because the reference has been
initialised to the address of a literal 2 or because a word access to
address 2 returns 2.
May 30 '06 #3
I tried running this:

unsigned const int& n = 3;
cout << n << endl;
cout << &n << endl;

Output is:
3
0012FEC8

During debugging I can see that memory location 0012FEC8 has the value
3 stored.

This is on VC++ 2003 compiler.

So this answers question 1.

2:

About the error you saw, MSDN says this:
'reference' : initialization of reference member requires a temporary
variable

A constructor initializes a reference to a member instead of
initializing the member.

It is invalid to initialize a reference member of a class in the
class's constructor with a temporary variable. An attempt to do so
generates the C2354 error, as illustrated by this sample code:

// C2354.cpp
int temp() { return 1; }
class Test
{
public:
int member;
int& ref_member;
Test();
};

Test::Test() : ref_member( temp() )
{ // C2354
}
When this error is encountered, the solution is to change the code so
that the reference member is not initialized to a temporary variable.
The reference must be initialized to an object that will exist for the
lifetime of the reference member.
------------------------------------------------------------------------------------

So it seems that the 2 in the constructor call is being treated as a
temporary variable. and not as something in the global memory.

May 30 '06 #4
shailesh wrote:
I tried running this:

unsigned const int& n = 3;
cout << n << endl;
cout << &n << endl;

Output is:
3
0012FEC8

During debugging I can see that memory location 0012FEC8 has the value
3 stored.

This is on VC++ 2003 compiler.

So this answers question 1.

2:

About the error you saw, MSDN says this:
'reference' : initialization of reference member requires a temporary
variable

A constructor initializes a reference to a member instead of
initializing the member.

It is invalid to initialize a reference member of a class in the
class's constructor with a temporary variable. An attempt to do so
generates the C2354 error, as illustrated by this sample code:

// C2354.cpp
int temp() { return 1; }
class Test
{
public:
int member;
int& ref_member;
Test();
};

Test::Test() : ref_member( temp() )
{ // C2354
}
When this error is encountered, the solution is to change the code so
that the reference member is not initialized to a temporary variable.
The reference must be initialized to an object that will exist for the
lifetime of the reference member.
------------------------------------------------------------------------------------

So it seems that the 2 in the constructor call is being treated as a
temporary variable. and not as something in the global memory.


Hi shailesh,

That's very interesting but the Microsoft compiler error that I saw was '
initialization of
reference member requires a temporary variable'. This is quite the opposite
of what the MSDN article says (reference member must NOT be initialised to a
temporary).

I'm a little more confused now :-(
May 30 '06 #5
"shailesh" <sh*******@gmail.com> wrote in message
news:11**********************@j33g2000cwa.googlegr oups.com

2:

About the error you saw, MSDN says this:
'reference' : initialization of reference member requires a temporary
variable

A constructor initializes a reference to a member instead of
initializing the member.

It is invalid to initialize a reference member of a class in the
class's constructor with a temporary variable. An attempt to do so
generates the C2354 error, as illustrated by this sample code:

// C2354.cpp
int temp() { return 1; }
class Test
{
public:
int member;
int& ref_member;
Test();
};

Test::Test() : ref_member( temp() )
{ // C2354
}
When this error is encountered, the solution is to change the code so
that the reference member is not initialized to a temporary variable.
The reference must be initialized to an object that will exist for the
lifetime of the reference member.
------------------------------------------------------------------------------------

So it seems that the 2 in the constructor call is being treated as a
temporary variable. and not as something in the global memory.


On the other hand, Comeau online compiles the code without complaint.

--
John Carson
May 30 '06 #6
John Carson wrote:
"shailesh" <sh*******@gmail.com> wrote in message
news:11**********************@j33g2000cwa.googlegr oups.com

2:

About the error you saw, MSDN says this:
'reference' : initialization of reference member requires a temporary
variable

A constructor initializes a reference to a member instead of
initializing the member.

It is invalid to initialize a reference member of a class in the
class's constructor with a temporary variable. An attempt to do so
generates the C2354 error, as illustrated by this sample code:

// C2354.cpp
int temp() { return 1; }
class Test
{
public:
int member;
int& ref_member;
Test();
};

Test::Test() : ref_member( temp() )
{ // C2354
}
When this error is encountered, the solution is to change the code so
that the reference member is not initialized to a temporary variable.
The reference must be initialized to an object that will exist for
the lifetime of the reference member.
------------------------------------------------------------------------------------

So it seems that the 2 in the constructor call is being treated as a
temporary variable. and not as something in the global memory.


On the other hand, Comeau online compiles the code without complaint.


Hi John, so does GCC 3.3.4 for ARM and it behaves as expected at run-time
too.
May 30 '06 #7
Tim Clacy posted:
1) Is this initialising the reference 'u' to the address of the
literal '2' or to the address 0x00000002?

unsigned const& u = 2;

C++ handles this under the hood as:
unsigned const literal_2 = 2;

unsigned const &u = literal_2;
2) What is the different between the initialisation of 'u' and 'S::u'
below?

unsigned const& u = 2;

struct S
{
unsigned const& u;

S() : u (2) { }

} s;

No difference. However, the global variable is far more likely to simply
be optimized to:

unsigned const u = 2;
VisualStudio 2005 generates "error C2354: 'S::u' : initialization of
reference member requires a temporary variable" but does not complain
about the initialisation of 'u'.

The code compiles without error and without warning with the G++
compiler.
When in doubt, presume Microsoft's incompetence.
-Tomás
May 30 '06 #8
Tomás wrote:
Tim Clacy posted:
1) Is this initialising the reference 'u' to the address of the
literal '2' or to the address 0x00000002?

unsigned const& u = 2;

C++ handles this under the hood as:
unsigned const literal_2 = 2;

unsigned const &u = literal_2;
2) What is the different between the initialisation of 'u' and 'S::u'
below?

unsigned const& u = 2;

struct S
{
unsigned const& u;

S() : u (2) { }

} s;

No difference. However, the global variable is far more likely to
simply be optimized to:

unsigned const u = 2;
VisualStudio 2005 generates "error C2354: 'S::u' : initialization of
reference member requires a temporary variable" but does not complain
about the initialisation of 'u'.

The code compiles without error and without warning with the G++
compiler.
When in doubt, presume Microsoft's incompetence.
-Tomás


Thanks very much Tomás
May 30 '06 #9

This discussion thread is closed

Replies have been disabled for this discussion.

Similar topics

4 posts views Thread by Samuele Armondi | last post: by
16 posts views Thread by Danny | last post: by
106 posts views Thread by A | last post: by
11 posts views Thread by A | last post: by
13 posts views Thread by Frederick Gotham | last post: by
4 posts views Thread by Kevin Frey | last post: by
6 posts views Thread by Taras_96 | last post: by
By using this site, you agree to our Privacy Policy and Terms of Use.