C++奇怪的钻石继承问题

发布于 2024-09-16 09:02:47 字数 723 浏览 6 评论 0原文

我有这个

    A
  /   \
 B     C
  \   /
    D

A 有一个纯虚函数,原型为:

virtual A* clone(void) const = 0;

B 和 C 实际上继承自 A ( class B: public virtual A, class C: public virtual A)

B具有虚函数,原型为:

virtual B* clone(void) const {}; 

C 具有虚函数,原型为:

virtual C* clone(void) const {};

D 继承自 B 和 B 。 C 像这样:class D: public B, public C D 有虚函数,原型为:

virtual D* clone(void) const {};

现在,编译时出现以下 6 行错误:

error C2250: 'D' : ambiguous inheritance of 'B *A::clone(void) const'

不知道如何解决这个问题。

提前致谢。

I have this

    A
  /   \
 B     C
  \   /
    D

A has a pure virtual function, prototyped as:

virtual A* clone(void) const = 0;

B and C virtually inherit from A ( class B: public virtual A, class C: public virtual A)

B has the virtual function, prototyped as:

virtual B* clone(void) const {}; 

C has the virtual function, prototyped as:

virtual C* clone(void) const {};

D inherits from both B & C like that: class D: public B, public C
D has the virtual function, prototyped as:

virtual D* clone(void) const {};

Now, when compiling I get the following 6 lines of errors:

error C2250: 'D' : ambiguous inheritance of 'B *A::clone(void) const'

No freaking idea how to solve this issue.

Thanks in advance.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

失与倦" 2024-09-23 09:02:47

如果您只需要层次结构中父级的一份副本,请使用虚拟继承。

class B : public virtual A

编辑:
MSVC++ 2010 中可能存在错误。Intellisense 未检测到问题,但编译器会卡住。奇怪的是 VC6 对此很满意。

作为解决方法,如果您按如下方式声明 D,它会使 MSVC++ 2010 满意,同时也可以在没有此问题的编译器中工作:

class D: public virtual A, public B, public C

Use virtual inheritance if you want only one copy of a parent in your hierarchy.

class B : public virtual A

Edit:
There may be a bug in MSVC++ 2010. The Intellisense doesn't detect a problem, but the compiler chokes on it. Strange since VC6 is happy enough with it.

As a workaround, if you declare D as follows, it makes MSVC++ 2010 happy while also working in compilers without this issue:

class D: public virtual A, public B, public C
2024-09-23 09:02:47

您在原始帖子中描述的内容完全合法。一个快速示例代码,完全由 Comeau Online 编译器进行编译,没有任何错误

class A {
public: virtual A* clone() const = 0;
};

class B: public virtual A {
public: virtual B* clone() const { return 0; }
};

class C: public virtual A {
public: virtual C* clone() const { return 0; }
};

class D: public B, public C
{
public: virtual D* clone() const { return 0; }
};

。要么您没有按照您所说的操作,要么您的编译器已损坏。发布您尝试编译的真实代码。

PS 我刚刚尝试在 VS 2010 Express 中编译它并得到相同的错误。正如 Gunslinger47 在评论中指出的那样,这是 VS 2010 编译器中的一个错误。

What you describe in your original post is perfectly legal. A quick sample code that does exactly that compiles without any errors by Comeau Online compiler

class A {
public: virtual A* clone() const = 0;
};

class B: public virtual A {
public: virtual B* clone() const { return 0; }
};

class C: public virtual A {
public: virtual C* clone() const { return 0; }
};

class D: public B, public C
{
public: virtual D* clone() const { return 0; }
};

Either you are not doing what you said you are doing, or your compiler is broken. Post real code you are trying to compile.

P.S. I just tried compiling this in VS 2010 Express and got the same error. As Gunslinger47 also suggests in the comments, this is a bug in VS 2010 compiler.

呆头 2024-09-23 09:02:47

避免钻石继承? ;->

无论如何,这里是示例(真正的示例 - 不要那样转换)

// ConsoleCppTest.cpp :定义控制台应用程序的入口点。
//

#include "stdafx.h"
#include "iostream"

class A {
public:
    virtual void* clone() = 0;
};

class B: public A {
public:
    virtual void* clone() = 0;
};

class C: public A {
    public:
    virtual void* clone() = 0;
};

class D: public B, public C
{
public:


    virtual void* B::clone() 
    {
        std::cout << "B";
        return (void*)this;
    }

    virtual void* C::clone()
    {
        std::cout << "C";
        return (void*)this;
    }
};

int _tmain(int argc, _TCHAR* argv[])
{

    D* d = new D();

    void* b = ((B*)d)->clone();

    void* c = ((C*)d)->clone();

    return 0;
}

avoid diamond inheritance? ;->

anyway, here is sample (really sample - don't cast like that)

// ConsoleCppTest.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include "iostream"

class A {
public:
    virtual void* clone() = 0;
};

class B: public A {
public:
    virtual void* clone() = 0;
};

class C: public A {
    public:
    virtual void* clone() = 0;
};

class D: public B, public C
{
public:


    virtual void* B::clone() 
    {
        std::cout << "B";
        return (void*)this;
    }

    virtual void* C::clone()
    {
        std::cout << "C";
        return (void*)this;
    }
};

int _tmain(int argc, _TCHAR* argv[])
{

    D* d = new D();

    void* b = ((B*)d)->clone();

    void* c = ((C*)d)->clone();

    return 0;
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文