C++ - 为什么这种菱形继承结构不会引起歧义?
C++ - Why isn't this structure of diamond inheritance cause an ambiguity?
我浏览了数十个多重继承问题,但未能找到该问题的答案。
我明白为什么这不会编译:
struct B{
virtual void f(){
printf("B");
}
};
struct C1 : virtual B{
void f() override{
printf("C1");
}
};
struct C2: virtual B{
void f() override{
printf("C2")
}
};
struct D: C1,C2{
};
因为无法确定 f
应该在 B
的 vtable 中。
但是,我很惊讶地看到这段代码可以编译:
struct B{
virtual void f(){
printf("B");
}
};
struct C1 : virtual B{
void f() override{
printf("C1");
}
};
struct C2: virtual B{
};
struct D: C1,C2{
};
我的(错误的)直觉是我们仍然有从 D
到 B
的两条路径,并且在每条路径中最后一个 f
被覆盖的地方是不同的 - 在一条路径中它是在 C1
中,在一个路径中它在 B
中,但这确实可以编译。
为什么这不会引起歧义?
因为 C1::f1 覆盖 B::f1,它将优先用于具有动态类型 C1 或任何子类的任何对象。
在模棱两可的情况下,虽然 C1::f1 和 C2::f1 都会覆盖 B::f1,但它们不会相互覆盖,所以歧义存在于它们之间——事实上它们都是重写一个公共基础函数是无关紧要的。
我浏览了数十个多重继承问题,但未能找到该问题的答案。
我明白为什么这不会编译:
struct B{
virtual void f(){
printf("B");
}
};
struct C1 : virtual B{
void f() override{
printf("C1");
}
};
struct C2: virtual B{
void f() override{
printf("C2")
}
};
struct D: C1,C2{
};
因为无法确定 f
应该在 B
的 vtable 中。
但是,我很惊讶地看到这段代码可以编译:
struct B{
virtual void f(){
printf("B");
}
};
struct C1 : virtual B{
void f() override{
printf("C1");
}
};
struct C2: virtual B{
};
struct D: C1,C2{
};
我的(错误的)直觉是我们仍然有从 D
到 B
的两条路径,并且在每条路径中最后一个 f
被覆盖的地方是不同的 - 在一条路径中它是在 C1
中,在一个路径中它在 B
中,但这确实可以编译。
为什么这不会引起歧义?
因为 C1::f1 覆盖 B::f1,它将优先用于具有动态类型 C1 或任何子类的任何对象。
在模棱两可的情况下,虽然 C1::f1 和 C2::f1 都会覆盖 B::f1,但它们不会相互覆盖,所以歧义存在于它们之间——事实上它们都是重写一个公共基础函数是无关紧要的。