🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: comp.std.c++
Article #3199

Re: Explicit constructor call vs Temporaries

#3199
From: Matt Austern
Date: Thu, 01 Feb 1996 22:54
72 lines
3095 bytes
In article <4eq5p2$fpu@fsuj01.rz.uni-jena.de> mkt@isun04.inf.uni-jena.de (Tilo Koerbs) writes:

>  About the error message in this posted code:
> 
> > class T {
> >   T();
> >   ~T();
> > }
> > 
> > class X {
> >   X();
> >   ~X();
> >   f(T& t);
> > }
> > 
> > int main() {
> >   X x;
> >   x.f(T());  // Compiler complained on this line
> > }
> 
> The 'temporary' (it is an UNNAMED) T()-object is NOT const!
> Consider:
> 	class T {
> 	public:
> 		T();
> 		~T();
> 		void nonConstFct() {}
> 	};
> 
> 	int main() {
> 		T().nonConstFct();  // Allowed!!!
> 	}
> 
> And so the compiler should have no problem with this code!
> I compiled it without any problem!

It's true that T().nonConstFct() is legal.  It's also true that 
x.f(T()) is illegal.  Those two cases are very different!

The issue isn't whether what T() returns is const, but whether it's an
lvalue.  This is a crucial point, since a non-const reference may not
be bound to an rvalue.  Unfortunately, you have to read section 8.5.3
[dcl.init.ref] a little bit carefully to see this; it's quite
unambiguous, though.  Paragraph 8 begins "--Otherwise [i.e. if a
reference is being initialized with an rvalue], the reference shall be
to a non-volatile const type (i.e., cv1 shall be const)."

(As usual, the complicated language in 8.5.3 simply formalizes what
you'd expect anyway.  Creating a reference to a temporary is a
problematic operation, so it's forbidden except in certain restricted
cases.)

And, indeed, the explicit invocation of a constructor yields an
rvalue.  The draft standard says this in several places, and implies
it in others.  One such place is section 3.10 [basic.lval], paragraph
5: "Constructor invocations and calls to functions that do not return
references are always rvalues."  See also the footnote to paragraph 2:
"Expressions such as invocations of constructors and of functions that
return a class type refer to objects, and the implementation can
invoke a member function upon such objects, but the expressions are
not lvalues."


-- 
Matt Austern
SGI: MTI Compilers Group
austern@isolde.mti.sgi.com

[ comp.std.c++ is moderated.  Submission address: std-c++@ncar.ucar.edu.
  Contact address: std-c++-request@ncar.ucar.edu.  The moderation policy is
  summarized in http://reality.sgi.com/employees/austern_mti/std-c++/policy.html
]
Technical Details
Message-ID: <AUSTERN.96Feb1104027@isolde.mti.sgi.com>
Path: arc1-ca.pugleaf.net!engnews1.Eng.Sun.COM!taumet!clamage
References: <4e6plv$idn@eclipse.eng.sc.rolm.com> <4eq5p2$fpu@fsuj01.rz.uni-jena.de>

Show Full Headers
Complete Article Headers
Path: arc1-ca.pugleaf.net!engnews1.Eng.Sun.COM!taumet!clamage
From: austern@isolde.mti.sgi.com (Matt Austern)
Newsgroups: comp.std.c++
Subject: Re: Explicit constructor call vs Temporaries
Date: 1 Feb 1996 22:54:42 GMT
Organization: SGI
Approved: clamage@eng.sun.com (comp.std.c++)
Message-ID: <AUSTERN.96Feb1104027@isolde.mti.sgi.com>
References: <4e6plv$idn@eclipse.eng.sc.rolm.com> <4eq5p2$fpu@fsuj01.rz.uni-jena.de>
Reply-To: austern@cardboard.mti.sgi.com
NNTP-Posting-Host: taumet.eng.sun.com
Content-Type: text
X-Nntp-Posting-Host: isolde.mti.sgi.com
In-Reply-To: mkt@isun04.inf.uni-jena.de's message of 01 Feb 1996 09:54:08 PST
Content-Length: 2096
X-Lines: 67
Originator: clamage@taumet