🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

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

Re: Constructors and conversion operator

#3775
From: Roman Lechtchinsky
Date: Fri, 22 Mar 1996 01:48
101 lines
5049 bytes
Steve Clamage wrote:
>
> In article 2E03@cs.tu-berlin.de, Roman Lechtchinsky
> <wolfro@cs.tu-berlin.de> writes:
> >Steve Clamage wrote:
> >>
> >> Suppose a copy constructor T::T(const T&) is viewed as a conversion
> >> from T to T. If such a conversion is "needed", the shortest conversion
> >> sequence must be chosen. That would be the null sequence, and so the
> >> copy ctor would never be used or even considered for that purpose.
> >> (Just as the sequence int->Rational->float would never be considered in
> >> converting an int to a float.)
> >
> >I'm not too sure here. First, if the copy constructor is the identity
> >conversion, why is it called at all? I mean, if the identity conversion is
> >eliminated from the conversion sequence, why isn't the call to the copy
> >constructor itself eliminated? Second, if the copy constructor is called,
> >why is it called only once? Consider
> >
> >class A { A(const A&); };
> >void foo(A);
> >A a;
> >
> >Now, foo(a) is implicitly converted to foo(A(a)). Why not to foo(A(A(a))?
>
> Let's not confuse type conversion with making a copy.

No, no, no... Not me, the draft does (IMO). Anyway, this question is a bit
off topic, I think. I'll try to explain this once more.

Part I.

This is what the DWP says about converting constructors:

1) A constructor declared without the  function-specifier  explicit  that
  can  be called with a single parameter specifies a conversion from the
  type of its first parameter to the type of its  class.   Such  a 
  constructor is called a converting constructor. [class.conv.ctor]

2) A  nonconverting  constructor  constructs objects just like converting
  constructors, but does so only where a constructor call is  explicitly
  indicated by the syntax. [class.conv.ctor]

This is what the DWP says about copy constructors:

  A constructor for class X is a copy constructor if its first parameter
  is of type X& or const X& and either there are no other parameters  or
  else  all other parameters have default arguments. [class.copy]

This means that per definitionem a copy constructor is a converting
constructor and thus a user-defined conversion. Note that nothing is said
about the types that participate in the conversion. In particular, it is
*not* said that the identity conversion is not a user-defined conversion.
Thus, everything the DWP says about user-defined conversions applies to
copy constructors.
This is what the DWP says about user-defined conversions:

  At most one user-defined conversion (constructor or  conversion 
  function) is implicitly applied to a single value. [class.conv.fct]

As you can see, the DWP doesn't even talk about converting types; it
mentions only applying user-defined conversions.
Now, let's return to my example:

class A { A(const A&); };
class B { operator A&(); };
void foo( A );
B b;

The call foo(b) requires that

a) the conversion operator B::A&() be applied to b;
b) the converting constructor A::A(const A&) be applied to the value returned
by the conversion operator B::A&().

Which makes two user-defined conversions implicitly applied to the single
value b. Hence the call is illegal.

Part II.

Now, let's see if the copy constructor is the identity conversion. The copy
constructor takes an argument of type A&, not A ( a constructor like A(A) is
illegal ). Look at the definition of converting constructors and substitute
"the type of its parameter" with A& and "the type of its class" with A. The
copy constructor specifies a conversion from A& to A. AFAIK, A& and A are
still different types. To me, this doesn't look like an identity conversion.

Well, the way you see this is certainly the way it should be. However, even
if I'm missing something, this all is rather unclear and the main advantage
of a standard is (should be) clarity. Thus, IMO the standard should contain
an explicit statement on this topic.

Bye

Roman
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]
Technical Details
Message-ID: <3151E556.5995@cs.tu-berlin.de>
Path: arc1-ca.pugleaf.net!in1.uu.net!bounce-back
References: <31505061.2E03@cs.tu-berlin.de> <4is5ao$dds@engnews1.Eng.Sun.COM>

Show Full Headers
Complete Article Headers
From: Roman Lechtchinsky <wolfro@cs.tu-berlin.de>
Message-ID: <3151E556.5995@cs.tu-berlin.de>
X-Original-Date: Fri, 22 Mar 1996 00:25:10 +0100
Path: arc1-ca.pugleaf.net!in1.uu.net!bounce-back
Date: 22 Mar 96 01:48:38 GMT
Approved: fjh@cs.mu.oz.au
Return-Path: <daemon@migs.UCAR.EDU>
Newsgroups: comp.std.c++
Subject: Re: Constructors and conversion operator
Organization: Technical University of Berlin
References: <31505061.2E03@cs.tu-berlin.de> <4is5ao$dds@engnews1.Eng.Sun.COM>
X-Mailer: Mozilla 2.0 (Win95; I)
X-Auth: PGPMoose V1.1 PGP comp.std.c++
 iQBFAgUBMVIHqOEDnX0m9pzZAQHfYQF/YDjmlWdCDMPBbaizCoAz2VQgpnPORefk
 Wemm+4IalfCBPi3Y/EWGOHrEM0vsjn44
 =HP4P