Doxygen 有一个非常巧妙的功能,它可以从代码生成继承图。但是,当使用来自具有公共基类的类的多重继承时,该图显示了两个单独的基类(即使我使用的是虚拟继承,如基类周围的虚线所示)

我怎样才能让 Doxygen 情节更像以下内容。. .
D
/ \
B C
\ /
A
Run Code Online (Sandbox Code Playgroud)
而不是:(就像没有虚拟继承一样)
D
/ \
B C
| |
A A
Run Code Online (Sandbox Code Playgroud) c++ doxygen multiple-inheritance virtual-inheritance diamond-problem
文字描述(下面的代码):我有一个提供类集合的库。对于每组类,我们有两个具体类型,( ClassA_Partial, ClassA), ( ClassB_Partial, ClassB) 等。其中每一个都分别实现 ( Interface_Partial, Interface) 。此外,Interface is a Interface_Partial和each Class? is a Class?_Partial - 创建一个菱形继承模式,其中顶部被虚拟继承。
为什么Interface_Partial函数在继承ClassAand时会产生二义性ClassB?
struct Interface_Partial
{
virtual ~Interface_Partial();
virtual void f() = 0;
};
struct Interface
:
virtual Interface_Partial
{
virtual void g() = 0;
};
struct ClassA_Partial : public virtual Interface_Partial
{
void f() {};
};
struct ClassA : public Interface, public virtual ClassA_Partial …Run Code Online (Sandbox Code Playgroud) c++ inheritance multiple-inheritance virtual-inheritance msvc12
struct A {
virtual void foo() { std::cout << "a";};
};
struct B:public virtual A {
void foo() { std::cout << "b";}
};
struct C:public virtual A {
void foo() { std::cout << "c";}
};
struct D:public B, public C {
};
int main() {
return 0;
}
Run Code Online (Sandbox Code Playgroud)
因此,在编译时会出现以下错误:
\main.cpp:16:8: error: no unique final overrider for 'virtual void A::foo()' in 'D'
struct D:public B, public C {
Run Code Online (Sandbox Code Playgroud)
如果我们将B和C结构的继承设为非虚拟的,则代码将正确编译而没有任何错误(但是,如果我们调用dd.foo(),则错误当然会发生)。那有什么区别呢?为什么当我们虚拟继承我们的类时出现错误,而如果直接继承则没有错误呢?
class A : public X;
class B : public virtual A;
class C : public virtual A;
class D1 : public B, public C;
class D2 : public B, public C;
void *p1 = new D1; //after storing the pointers,
void *p2 = new D2; //there will be no exact type info.
A *pA1 = (A *) p1; // Cast 1
A *pA2 = (A *) p2;
X *pX1 = (X *) p1; // Cast 2
X *pX2 = (X …Run Code Online (Sandbox Code Playgroud) 我想了解为什么 C++ 标准要求虚拟基非默认构造函数不能由中间非最派生类调用,如这段代码中所示,当使用 '-D_WITH_BUG_' 编译时:
/* A virtual base's non-default constructor is NOT called UNLESS
* the MOST DERIVED class explicitly invokes it
*/
#include <type_traits>
#include <string>
#include <iostream>
class A
{
public:
int _a;
A(): _a(1)
{
std::cerr << "A() - me: " << ((void*)this) << std::endl;
}
A(int a): _a(a)
{
std::cerr << "A(a) - me:" << ((void*)this) << std::endl;
}
virtual ~A()
{
std::cerr << "~A" << ((void*)this) << std::endl;
}
};
class B: public virtual …Run Code Online (Sandbox Code Playgroud) 我在项目中有一个案例,我需要将一个抽象类虚拟地继承到两个不同的类中,这两个类再次继承到最终类中,但编译器一直向我显示此错误
error C2250: 'D': ambiguous inheritance of 'B &A::doit(void)'
Run Code Online (Sandbox Code Playgroud)
如何消除此类错误,类示例如下
error C2250: 'D': ambiguous inheritance of 'B &A::doit(void)'
Run Code Online (Sandbox Code Playgroud)
我尝试先删除基类函数,但似乎不起作用。
struct B { int i; };
struct D1 : virtual B {};
struct D2 : B {}; // <-- not virtual
struct DD : D1, D2 {};
Run Code Online (Sandbox Code Playgroud)
上面已经编码,还是编译器的需求D2也将virtual:
DD d;
d.i = 0; // error: request for member `i' is ambiguous
Run Code Online (Sandbox Code Playgroud)
我不明白的是,一旦你提示编译器B是virtual关于DD(via D1)那么为什么它仍然i是模棱两可的?
(如果我的内存服务正确,那么旧的VC++(2006年)就足以用单virtual继承来证明这一点)
考虑经典的虚拟继承钻石层次结构.我想知道在这种层次结构中复制和交换习语的正确实现是什么.
这个例子有点人为 - 并且它不是很聪明 - 因为它可以很好地使用A,B,D类的默认复制语义.但只是为了说明问题 - 请忘记示例弱点并提供解决方案.
所以我从两个基类(B <1>,B <2>)派生出D类 - 每个B类几乎从A类继承.每个类都有非平凡的复制语义,使用复制和交换习语.派生最多的D类在使用这个习语时有问题.当它调用B <1>和B <2>交换方法时 - 它将虚拟基类成员交换两次 - 所以一个子对象保持不变!
A:
class A {
public:
A(const char* s) : s(s) {}
A(const A& o) : s(o.s) {}
A& operator = (A o)
{
swap(o);
return *this;
}
virtual ~A() {}
void swap(A& o)
{
s.swap(o.s);
}
friend std::ostream& operator << (std::ostream& os, const A& a) { return os << a.s; }
private:
S s;
};
Run Code Online (Sandbox Code Playgroud)
乙
template <int N> …Run Code Online (Sandbox Code Playgroud) c++ multiple-inheritance virtual-inheritance diamond-problem copy-and-swap
使用虚拟继承时类的大小如下
ABase=4(sizeof imem)
BBase=12(sizeof imem+ABase+VBase_ptr)
CBase=12(sizeof imem+ABase+VBase_ptr)
Run Code Online (Sandbox Code Playgroud)
这是有道理的,但我不明白为什么大小ABCDerived是24.
class ABase{
int iMem;
};
class BBase : public virtual ABase {
int iMem;
};
class CBase : public virtual ABase {
int iMem;
};
class ABCDerived : public BBase, public CBase {
int iMem;
};
Run Code Online (Sandbox Code Playgroud) 请考虑以下代码:
#include <iostream>
class A
{
public:
virtual void f() = 0;
virtual void g() = 0;
};
class B : virtual public A
{
public:
virtual void f()
{
g();
}
};
class C : virtual public A
{
public:
virtual void g()
{
std::cout << "C::g" << std::endl;
}
};
class D : public C, public B
{
};
int main()
{
B* b = new D;
b->f();
}
Run Code Online (Sandbox Code Playgroud)
以下程序的输出是C::g.
编译器如何调用类B的姐妹类的函数?
c++ inheritance overriding multiple-inheritance virtual-inheritance
c++ ×10
inheritance ×3
c++17 ×1
casting ×1
constructor ×1
doxygen ×1
msvc12 ×1
overriding ×1
virtual ×1