Topic: Ambiguity between the constructors
Author: dbkruger@ix.netcom.com (Dov Kruger )
Date: 1996/07/01 Raw View
>> I have a class something like this :
>> class A { A() {}
>> public : A(int=5) {}
>> };
>>
>> main()
>> { A a;}
No one really answered the direct question:
The reason there is an error is NOT because there is ambiguity
over which function the caller should call.
The only function the caller would have the right to call is the
public one, so there is no ambiguity about which function to call.
The error message is confusing.
The problem is that the two functions mangle to the same name,
and you have two different implementations for the same function.
Internally, your compiler simply can't handle that (defining
the same symbol twice), and the standard agrees that the compiler
should generate an error not when the ambiguous function is _called_,
but when the same function is defined twice.
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]
Author: "Ian D. Horwill" <Ian@horwill.demon.co.uk>
Date: 1996/07/01 Raw View
In article <66ybl9mxma.fsf@heaven.india.ti.com>, Kalpesh Shah
<anil@india.ti.com> writes
>I have a class something like this :
>
> class A {
> A() {}
> public :
> A(int=5) {}
> };
>
> main()
> {
> A a;
> }
>
>
>When I try to compile this code, I get the error msg saying
>
> " Error: Overloading ambiguity between A::A() and A::A(int) "
>
>
>QUESTION :
>
> Since only one of the constructor is available to the outside world,
> * why can't the compiler resolve this ?
> * what does the C++ language says in this regard ?
ARM, Section 10.1.1 Ambiguities
"The check for ambiguity takes place before access control."
"If the name of an overloaded function is unambiguously found
overloading resolution also takes place before access control."
--
Ian D. Horwill
Really Useful Software Ltd.
ian@horwill.demon.co.uk 100441.3700@compuserve.com
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]
Author: clamage@Eng.sun.com (Steve Clamage)
Date: 1996/07/01 Raw View
In article o5b@sjx-ixn5.ix.netcom.com, dbkruger@ix.netcom.com (Dov Kruger ) writes:
>>> I have a class something like this :
>>> class A { A() {}
>>> public : A(int=5) {}
>>> };
>>>
>>> main()
>>> { A a;}
>
>No one really answered the direct question:
>
>The reason there is an error is NOT because there is ambiguity
>over which function the caller should call.
>
>The only function the caller would have the right to call is the
>public one, so there is no ambiguity about which function to call.
>The error message is confusing.
Sorry, your analysis is not correct.
The C++ rule has always been that overload resolution occurs before
access is checked. You can find that rule in the ARM, and it is
unchanged in the draft standard. You can also find the reason for
that rule in the ARM and in "Design and Evolution".
>The problem is that the two functions mangle to the same name,
>and you have two different implementations for the same function.
No, that is not correct either.
The private constructor has no parameters, and the public constructor
has one int parameter. The function types are different, and, assuming
name mangling is used to implement function linkage (which is not a
requirement), the names must be mangled differently.
The error message is exactly right. Both constructors can be called
without any explicit argument. (The compiler would supply an int
argument of value 5 implicitly if the public version could be called
unambiguously.) If an A constructor is invoked without any explicit
argument, there is no way to choose between the constructors at the
time function overloading is resolved.
Generally speaking, default argument values and overloading don't mix
very well -- there is too much chance for ambiguity, as in this example.
Suggested design guideline: Provide just one function with default argument
values, or provide overloaded functions having no default argument values.
---
Steve Clamage, stephen.clamage@eng.sun.com
[ 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 ]
Author: jodle@bix.com (jodle)
Date: 1996/07/04 Raw View
Dov Kruger (dbkruger@ix.netcom.com) wrote:
: No one really answered the direct question:
Actually, they did. The ARM -requires- that access be disregarded when
selecting candidates for function call.
: The error message is confusing.
Only if your understanding of the language is incomplete in this area.
: The problem is that the two functions mangle to the same name,
: and you have two different implementations for the same function.
Name mangling is not the problem. In fact, theoretically, name mangling
need not even occur. In practical terms, name mangling is only an issue
germaine to the process of linking because it provides a way to predict
the names of symbols with definitions that are not visible within a given
translation unit. The two functions cited should not mangle to the same
name. The function that takes an integer argument gets "int" hashed into
its name (perhaps not literally). The default value is provided by
generating code at the call point to pass that value. That is a key
reason default values are provided in the function declaration rather than
the function definition.
: Internally, your compiler simply can't handle that (defining
: the same symbol twice), and the standard agrees that the compiler
: should generate an error not when the ambiguous function is _called_,
: but when the same function is defined twice.
This assertion is incorrect and logically inconsistent. If the compiler
could not distinguish between the two names, it would be necessary for it
to report an error when it encountered the second clashing name, not when
a call using the name was attempted. Furthermore, while this specific
case would seem to indicate that it is trivial for the compiler to detect
ambiguity early, it is impossible for the compiler to predict what
conversions may be introduced by classes that have not yet been declared
and their impact on less obvious function pairs.
I would even argue that it would be worse for the compiler to complain
about an ambiguity between ctor() and ctor(int=5) if a call to ctor() is
never made than it is for the compiler to complain about ambiguity "late".
In my opinion, "late" is just exactly on time.
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]
Author: anil@india.ti.com (Kalpesh Shah)
Date: 1996/06/27 Raw View
I have a class something like this :
class A {
A() {}
public :
A(int=5) {}
};
main()
{
A a;
}
When I try to compile this code, I get the error msg saying
" Error: Overloading ambiguity between A::A() and A::A(int) "
QUESTION :
Since only one of the constructor is available to the outside world,
* why can't the compiler resolve this ?
* what does the C++ language says in this regard ?
---
Anil Kumar, email : anil@india.ti.com
Software Engg Group
Texas Instruments Inc.
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]
Author: Eric Gindrup <gindrup@okway.okstate.edu>
Date: 1996/06/27 Raw View
Kalpesh Shah wrote:
>
> I have a class something like this :
> class A { A() {}
> public : A(int=5) {}
> };
>
> main()
> { A a;}
>
> When I try to compile this code, I get the error msg saying
> " Error: Overloading ambiguity between A::A() and A::A(int) "
>
> QUESTION :
> Since only one of the constructor is available to the outside world,
> * why can't the compiler resolve this ?
Because the compiler can't tell the two functions apart. They have
the same signature and therefore must be the same function, but...
they aren't. The Standard addresses this.
> * what does the C++ language says in this regard ?
In short:
Default arguments are not used to disambiguate overloaded functions.
[...]
> Anil Kumar, email : anil@india.ti.com[...]
-- Eric Gindrup ! gindrup@okway.okstate.edu
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]
Author: drew@qualcomm.com (Drew Eckhardt)
Date: 1996/06/28 Raw View
In article <66ybl9mxma.fsf@heaven.india.ti.com>,
Kalpesh Shah <anil@india.ti.com> wrote:
> class A {
> A() {}
> public :
> A(int=5) {}
> };
[ snip ]
with instantiation of A resulting in the following error :
> " Error: Overloading ambiguity between A::A() and A::A(int) "
As expected.
>QUESTION :
> Since only one of the constructor is available to the outside world,
> * why can't the compiler resolve this ?
C++ compilers resolve scope, followed by overloading, and finally access
control in three separate steps.
> * what does the C++ language says in this regard ?
Chapter 13 of the Arm covers overloading, and if you treat it as a
lawyer would (assume nothing), it will explain this behavior.
--
<a href="http://www.poohsticks.org/drew/">Home Page</a>
Four boxes : soap, ballot, jury, ammo. | Work: drew@Qualcomm.COM
Use in that order. | Play: drew@PoohSticks.ORG
---
[ 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 ]
Author: etmhuzw@ericsson.se (F. Hugo Zwaal)
Date: 1996/06/28 Raw View
In article <66ybl9mxma.fsf@heaven.india.ti.com>, anil@india.ti.com (Kalpesh Shah) writes:
> I have a class something like this :
>
> class A {
> A() {}
> public :
> A(int=5) {}
> };
>
> main()
> {
> A a;
> }
>
>
> When I try to compile this code, I get the error msg saying
>
> " Error: Overloading ambiguity between A::A() and A::A(int) "
>
>
> QUESTION :
>
> Since only one of the constructor is available to the outside world,
> * why can't the compiler resolve this ?
> * what does the C++ language says in this regard ?
ANSWER:
* the compiler can't resolve this because you have specified a default argument
for the second constructor. So the compiler can't choose between the first
(default) constructor or the second constructor (with the default argument set
to 5).
* the C++ language says that this is an overloading ambiguity, just as the
compiler mentions.
Groets, Hugo.
[ moderator's note: the key point is that overloading has always
been supposed to be resoved before access is checked. See the ARM
Chapter 13, for example. -sdc ]
[ 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 ]