c++ - 没有虚拟继承的多重继承

标签 c++ inheritance multiple-inheritance virtual-inheritance

我试图理解多重继承,这是我的代码:

struct A {
  A() {}
  static int n;
  static int increment() { return ++n; }
};
int A::n = 0;

struct B : public A {};
struct C : public A {};
struct D : public B, C {};

int main() {
  D d;
  cout<<d.increment()<<endl;
  cout<<d.increment()<<endl;
}

此代码有效。但是,如果我将 increment() 更改为非静态,它将失败。

我的问题:

  1. 为什么编译器提示非静态版本的 increment() 的调用不明确,而静态版本却满足?
  2. 如果我向 B 或 C 添加另一个 increment() 函数,编译器也会报错,甚至声明为静态的。为什么?

最佳答案

模棱两可是什么意思?

编译器在给定上下文无法决定调用哪个函数时会提示调用不明确。因此,为了理解投诉,您必须检查可能存在的歧义。

Why compiler complains ambiguous call of non-static version of increment(), while satisfies with the static one?

根据定义,static类的功能不依赖于类的任何实例。您可以将其称为 A::increment(),这一事实强调了这一点。 (看,没有实例)。

菱形继承的问题不是编译器不知道执行哪个代码,而是不知道哪个this提供(您的 A 对象中有两个 D,一个包含在 B 中,一个包含在 C 中)。

当您使用 static A的功能, 没有隐式 this已通过,所以没有问题;如果您尝试使用非 static函数,则编译器无法决定是否 this应该指向 AB或在 C , 这是模棱两可的。

If I add another increment() function to B or C, compiler will complain too, even declared as static. Why?

此时,编译器可能会在 B::increment() 之间进行选择和 C::increment() ,它应该选择哪个?这是模棱两可的。

当你有一个线性层次结构时,它会调用与其“最接近”的层次结构(将那些隐藏在继承树的下方),但这里 BC是两个独立的分支,没有“更好”的分支。

注意:即使 B不执行 increment , 自 A你可以调用B::increment()吗实际上调用A::increment() . C也是如此.

关于c++ - 没有虚拟继承的多重继承,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25377040/

相关文章:

c++ - "#define FOO(template)"是做什么的?

c# - 为什么 C# 允许通过接口(interface)扩展方法而不是类进行多重继承?

c++ - 是什么导致 OpenSSL 出现段错误?

c++ - 从 C++ 中的基调用潜在 child 的构造函数

c++ - 检查 LLVM pass 中的后缘

c# - 组合应该专门用于继承还是在某些情况下不应该使用?

c++重载和覆盖operator +

php - 如果子类不定义构造函数,是否可以直接使用父类(super class)的构造函数?

c++ - 使用父类方法覆盖的多重继承

python - 多重继承 --> Fish.__init__() 缺少 2 个必需的位置参数