【问题标题】:Avoid multiple inheritance induced ambiguity by using scope resolution通过使用范围解析避免多重继承引起的歧义
【发布时间】:2018-03-20 16:22:30
【问题描述】:
这是一个多重继承的例子。我使用范围解析运算符来解决歧义而不是虚拟类。
struct A
{
int i;
};
struct B : A
{};
struct C : A
{};
struct D: B, C
{
void f()
{
B::i = 10;
}
void g()
{
std::cout << B::i <<std::endl;
}
};
int main()
{
D d1;
d1.f();
d1.g();
return 0;
}
B::i 格式正确吗?
【问题讨论】:
标签:
c++
c++11
inheritance
multiple-inheritance
diamond-problem
【解决方案1】:
B::i 格式正确吗?
是的,是的。最中肯的参考是[class.qual]/1:
如果限定 ID 的嵌套名称说明符指定了一个类,则
在嵌套名称说明符之后指定的名称在
类的范围,但下面列出的情况除外。 名称
应代表该类别或其其中之一的一名或多名成员
基类。
它指定您可以命名i,因为它是B 的基础成员。仅在之后检查可访问性,在您的情况下它是公开的。
[class.access.base]/5
... 对成员的访问受所在类的影响
成员被命名。这个命名类是成员所在的类
查找并找到名称...此时可以访问成员 m
R 当在类 N 中命名时,如果
- 存在可在 R 访问的 N 的基类 B,当在类 B 中命名时,m 可在 R 访问。
【解决方案2】:
是的。这些是 c++ 标准语法规则的摘录:
id-expression:
unqualified-id
qualified-id
postfix-expression:
[...]
postfix-expression . template[opt] id-expression
[...]
在 [class.mcft.non-static] 中:
当 id 表达式 (8.1) 不是类成员访问语法 (8.2.5) 的一部分并且不用于形成
指向成员 (8.3.1) 的指针在可以使用 this 的上下文 (8.1.2) 中用于类 X 的成员中,如果
名称查找 (6.4) 将 id 表达式中的名称解析为某个类的非静态非类型成员
C,并且如果 id-expression 可能被求值或者 C 是 X 或 X 的基类,则 id-expression 是
使用 (*this) (12.2.2.1) 作为后缀表达式转换为类成员访问表达式 (8.2.5)
的左侧。运算符。