Topic: Pointless ambiguity??
Author: "Ivan Godard" <igodardA@TpacbellDO.Tnet>
Date: Sat, 4 Sep 2004 22:57:38 GMT Raw View
struct A { void foo() {}};
struct B {void foo(int){}};
struct C : public A, public B {};
int main () {
C c;
c.foo();
c.foo(5);
}
The compilers (gcc, Comeau) reject the calls as ambiguous. I'm sure the
compilers conform, but can someone explain the rationale why the standard
should prohibit this rather than simply applying overload resolution? D&E is
silent on the matter.
Ivan
---
[ 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 ]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.jamesd.demon.co.uk/csc/faq.html ]
Author: Barry Margolin <barmar@alum.mit.edu>
Date: Mon, 6 Sep 2004 15:22:41 GMT Raw View
In article <Lgp_c.15876$eI4.9718@newssvr29.news.prodigy.com>,
"Ivan Godard" <igodardA@TpacbellDO.Tnet> wrote:
> struct A { void foo() {}};
> struct B {void foo(int){}};
> struct C : public A, public B {};
>
> int main () {
> C c;
> c.foo();
> c.foo(5);
> }
>
> The compilers (gcc, Comeau) reject the calls as ambiguous. I'm sure the
> compilers conform, but can someone explain the rationale why the standard
> should prohibit this rather than simply applying overload resolution? D&E is
> silent on the matter.
Because overload resolution is performed only on functions with the same
name. In your case you have two different functions, A::foo() and
B::foo().
Another way to look at it is that you always search the class hierarchy
for a member first. Then you perform steps like access checks and
overload resolution.
--
Barry Margolin, barmar@alum.mit.edu
Arlington, MA
*** PLEASE post questions in newsgroups, not directly to me ***
---
[ 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 ]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.jamesd.demon.co.uk/csc/faq.html ]
Author: brangdon@cix.co.uk (Dave Harris)
Date: Tue, 7 Sep 2004 03:05:36 GMT Raw View
igodardA@TpacbellDO.Tnet (Ivan Godard) wrote (abridged):
> struct A { void foo() {}};
> struct B {void foo(int){}};
> struct C : public A, public B {};
>
> int main () {
> C c;
> c.foo();
> c.foo(5);
> }
>
> The compilers (gcc, Comeau) reject the calls as ambiguous. I'm sure the
> compilers conform, but can someone explain the rationale why the
> standard should prohibit this rather than simply applying overload
> resolution? D&E is silent on the matter.
As I recall, there is a good explanation in the Annotated Reference
Manual, but I don't have my copy to hand. Briefly, the concern is really
about signatures which are more similar.
struct A { void foo( double ); };
struct B { void foo( int ); };
struct C : public A, public B {};
int main() {
C c;
c.foo( 0 ); // Error?
}
Here foo(int) is unambiguously the best match and would be found by
overload resolution if both functions were declared in C. However, they
are, in fact, declared in widely different places. Their interaction may
not have been considered. For example, perhaps A::foo() was written first,
then main() was written to call it, and then some other programmer added
B::foo() without knowing about C or main(). The meaning of the existing
code would silently change.
The C++ designers felt this was too error-prone. (It is more likely if the
class hierarchy is big and complex, of course.) The author of C can make
their intention clear with using declarations.
It's an interesting decision, and a place where C++ trades convenience for
safety. I believe Java makes the opposite choice. I don't know if it has
caused real problems there.
-- Dave Harris, Nottingham, UK
---
[ 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 ]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.jamesd.demon.co.uk/csc/faq.html ]