Forums before death by AOL, social media and spammers... "We can't have nice things"
|    comp.lang.c++.moderated    |    Moderated discussion of C++ superhackery    |    33,346 messages    |
[   << oldest   |   < older   |   list   |   newer >   |   newest >>   ]
|    Message 31,961 of 33,346    |
|    Johannes Schaub to All    |
|    Re: Resolution of ambiguous members in m    |
|    29 Feb 12 03:55:25    |
   
   From: schaub.johannes@googlemail.com   
      
   Am 22.02.2012 17:11, schrieb Thomas Richter:   
   > If a class inheriting is a member of a same name from two distinct   
   > bases, as in the following example:   
   >   
   > struct A {   
   > int a;   
   >   
   > A()   
   > : a(1)   
   > { }   
   > };   
   >   
   > struct B {   
   > int a;   
   >   
   > B()   
   > : a(1)   
   > { }   
   > };   
   >   
   > struct C : public A,B {   
   >   
   > int getA()   
   > {   
   > return a;   
   > }   
   > };   
   >   
   > int main(int argc,char **argv)   
   > {   
   > struct C c;   
   >   
   > return c.getA();   
   > }   
   >   
   > the compiler clearly refuses the code on the basis that C::a could be   
   > either A::a or B::a. Somehow, I had the expectation that inserting a   
   >   
   > struct C : public A,B {   
   > using A::a; // <---   
   > int getA()   
   > {   
   > return a;   
   > }   
   > };   
   >   
   > should resolve this ambiguity, as it expresses what I would prefer to   
   > do, but apparently, this is not the case.   
      
   C++03 says that you first collect any declaration of any member name   
   called 'a' declared in any subobject (*subobject*, not class!). A   
   declaration in an object hides a declaration in all its base class   
   subobjects. It then says that a using-declaration "using X::y;" is   
   considered to be from each baseclass-subobjects of type "X".   
      
   The two interpretations of this originate from the time you adjust the   
   subobject-affinity of a using-declaration.   
      
   1) If you first do hiding and then do the adjustment (from C to C::A) in   
   your case, then you end up with a single declaraton found in subobject   
   C::A (found by your using-declaration which did hide both C::A::a and   
   C::B::a).   
      
   2) If you first do the adjustment (from C to C::A), and then do hiding,   
   you end up with three declarations found in two different subobjects   
   (C::A and C::B). This will be an error.   
      
   Only the first choice of interpretation will make your program be valid.   
   Possibly your compiler takes option "2)" and rejects your code for a   
   lookup ambiguity. In DR #39   
   (http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#39), the   
   committee applied option "1)" for deeming a different code invalid, but   
   they also say that the outcome of that route is undesired.   
      
   C++11 makes your code unambiguous unambiguously, however compilers need   
   to implement the C++11 rules first. Last time I checked, Clang and GCC   
   didn't do so yet.   
      
      
   --   
    [ See http://www.gotw.ca/resources/clcm.htm for info about ]   
    [ comp.lang.c++.moderated. First time posters: Do this! ]   
      
   --- SoupGate-Win32 v1.05   
    * Origin: you cannot sedate... all the things you hate (1:229/2)   
|
[   << oldest   |   < older   |   list   |   newer >   |   newest >>   ]
(c) 1994, bbs@darkrealms.ca