2009-01-22 12 views
10

Der folgende Code generiert die Warnung C4250. Meine Frage ist, was ist die beste Lösung dafür?Visual Studio Compilerwarnung C4250 ('class1': erbt 'class2 :: member' über Dominanz)

class A 
{ 
    virtual void func1(); 
} 

class B : public A 
{ 
} 

class C : public A 
{ 
    virtual void func1(); 
} 

class D : public B, public C 
{ 
} 

int main() 
{ 
    D d; 
    d.func1(); // Causes warning 
} 

Nach dem, was ich gelesen habe, sollte es möglich sein, dies zu tun:

class D : public B, public C 
{ 
    using B::func1(); 
} 

Aber das ist eigentlich nichts tun. Die Art, wie ich es zur Zeit gelöst habe, ist:

class D : public B, public C 
{ 
    virtual void func1() { B::func1(); } 
} 

Was ist die Sicht von jedermann darauf?

+0

Der Code im ersten Block wird nicht kompiliert, und nach dem Kompilieren wird C4250 nicht generiert. – quamrana

Antwort

7

Haben Sie versucht, öffentliche virtuelle von Klasse A zu erben? Ich denke, es sollte es lösen.


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

Die virtuelle Vererbung soll die Mehrdeutigkeit lösen.

+1

Ja, sogar mit virtueller Vererbung hat es immer noch das gleiche Problem (es gibt zwei geeignete Funktionen zum Aufruf, der Compiler wählt nur die am häufigsten "überschriebenen") –

+0

Dann denke ich, es gibt keine Flucht aus Ihrer vorgeschlagenen Lösung. –

+3

Ich kompilierte Ihren Code jetzt in VS2005 und ohne das virtuelle ist es eigentlich ein Fehler, keine Warnung. Mit dem virtuellen ist es eine Warnung. –

0

Ich denke, die Lösung, die Sie verwenden, ist möglicherweise der Weg zu gehen, tut mir leid zu sagen. Das einzige, was mir dabei helfen kann, ist, wenn Sie A's func1 rein virtuell machen können. Das ist in Ihrem echten Programm allerdings nicht möglich.

+1

Leider gibt es einen Fehler in Visual Studio, was bedeutet, dass eine Warnung immer noch erscheint;) –

18

ich die gleiche Warnung für den folgenden Code hatte:

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

class Implementation : public virtual Interface 
{ 
public: 
    virtual void A() {}; 
}; 

class ExtendedInterface : public virtual Interface 
{ 
    virtual void B() = 0; 
}; 

class ExtendedImplementation : public ExtendedInterface , public Implementation 
{ 
public: 
    virtual void B() {}; 
}; 

Diese bug report für Visual C++ 2005 in Msdn legt nahe, dass dies ein bekannter Fehler, die nicht wichtig genug angesehen wurde zu reparieren ... Sie schlagen zu Deaktivieren Sie die Warnung in diesem Fall, indem Sie ein Pragma verwenden. Ich denke, es ist auch in Ihrem Fall sicher, aber Sie sollten virtuelle Vererbung verwenden, wie in der Antwort von Gal Goldman gezeigt.

0

Leicht

class A 
{ 
    virtual void func1(); 
} 

class B : public A 
{ 
} 

class C : public A 
{ 
    virtual void func1(); 
} 

class D : public B, public C 
{ 
    virtual void func1() 
    { 
    C::func1(); 
    } 
} 

int main() 
{ 
    D d; 
    d.func1(); // Causes warning 
} 
1

[A Kommentar wirklich, aber ich habe nicht genug rep ...] lösen

David Segonds identifiziert dies als einen bekannten Fehler in VS 2005, habe gerade versucht, seinem Beispiel Code in VS 2008 und es zeigt das gleiche Problem.