class member name lookup issues

Z

ZMZ

Hi all,

I am very confused about the standard n3225 10.2/13,

[ Note: Even if the result of name lookup is unambiguous, use of a
name found in multiple subobjects might still be ambiguous (4.11,
5.2.5, 5.3.1, 11.2).—end note ] [ Example:

struct B1 {
void f();
static void f(int);
int i;
};
struct B2 {
void f(double);
};
struct I1: B1 { };
struct I2: B1 { };
struct D: I1, I2, B2 {
using B1::f;
using B2::f;
void g() {
f(); // Ambiguous conversion of this
f(0); // Unambiguous (static)
f(0.0); // Unambiguous (only one B2)
int B1::* mpB1 = &D::i; // Unambiguous
int D::* mpD = &D::i; // Ambiguous conversion
}
};
I cannot see why this is unambiguous int B1::* mpB1 = &D::i; //
Unambiguous

Visual C++, Gcc and CLang all say that it is ambiguous access to D::i!

The wording seems to be related to the core issue #39
http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#39, and
the final proposal is here: http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2004/n1626.pdf

I now find that the new algorithm-based wordings (10.2/3-10.2/6) are
even more confusing because none of the note in 10.2/9, 10.2/10,
10.2/11, and 10.2/13 fully complies with 10.2/3-10.2/6. I can take
10.2/9-10.2/11 as exceptions, but I am especially confused about
10.2/13. I have no idea on the intention of 10.2/13.

How should the example in 10.2/13 be looked-up according to the
10.2/3-10.2/6? What's the intention of 10.2/13, i.e., what's the
situation of which 10.2/13 is considered as an exception of
10.2/3-10.2/6?

Please give me some hints. Thank you very much.
 
J

Johannes Schaub (litb)

ZMZ said:
Hi all,

I am very confused about the standard n3225 10.2/13,

[ Note: Even if the result of name lookup is unambiguous, use of a
name found in multiple subobjects might still be ambiguous (4.11,
5.2.5, 5.3.1, 11.2).—end note ] [ Example:

struct B1 {
void f();
static void f(int);
int i;
};
struct B2 {
void f(double);
};
struct I1: B1 { };
struct I2: B1 { };
struct D: I1, I2, B2 {
using B1::f;
using B2::f;
void g() {
f(); // Ambiguous conversion of this
f(0); // Unambiguous (static)
f(0.0); // Unambiguous (only one B2)
int B1::* mpB1 = &D::i; // Unambiguous
int D::* mpD = &D::i; // Ambiguous conversion
}
};
I cannot see why this is unambiguous int B1::* mpB1 = &D::i; //
Unambiguous

&D::i has type "int B1::*", and unambiguously refers to data member "i" of
B1. If you dereference it with a D object or if you assign it to a "int
D::*", you will get an ambiguity as needed.
Visual C++, Gcc and CLang all say that it is ambiguous access to D::i!

None of those compilers implement 10.2 yet.

The wording seems to be related to the core issue #39
http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#39, and
the final proposal is here:
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2004/n1626.pdf

I now find that the new algorithm-based wordings (10.2/3-10.2/6) are
even more confusing because none of the note in 10.2/9, 10.2/10,
10.2/11, and 10.2/13 fully complies with 10.2/3-10.2/6. I can take
10.2/9-10.2/11 as exceptions, but I am especially confused about
10.2/13. I have no idea on the intention of 10.2/13.

You need to give examples that show what you don't understand.
How should the example in 10.2/13 be looked-up according to the
10.2/3-10.2/6? What's the intention of 10.2/13, i.e., what's the
situation of which 10.2/13 is considered as an exception of
10.2/3-10.2/6?

The new algorithm based lookup rules decouples runtime concerns (finding an
unique object) from compile time/lookup concerns (finding a declaration that
a name refers to).

The following is well-formed with the new wording:

struct Z { int z; };
struct X : Z { };
struct Y : Z { };
struct A : X, Y { };

struct B : A {
using A::z;
};

The declaration "using A::x;" introduces a member name into A that refers to
the declaration "Z::z". In a declarative context, this is perfectly fine. An
error is risen only when you access "B::z" as a member access expression
(5.2.5).

There is currently a confusion about using declarations in general though,
in my opinion. A using declaration introduces a new member name into a
scope. Name lookup looks through the using declaration, but some paragraphs
in the spec assumes it doesn't (overload resolution in particular). A second
problem, in my opinion, is that 10.2p3 says "type declarations are replaced
by the types they designate". That doesn't make sense: "typedef int type;"
what will a lookup for "type" yield?
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,580
Members
45,054
Latest member
TrimKetoBoost

Latest Threads

Top