MSVC9.0漏洞还是对虚拟继承和朋友的误解?

时间:2010-10-10 11:56:41

标签: c++ visual-studio-2008 friend virtual-inheritance default-copy-constructor

考虑以下代码:

class A
{
    friend class B;
    friend class C;
};

class B: virtual private A
{
};

class C: private B
{
};

int main()
{
    C x; //OK default constructor generated by compiler
    C y = x; //compiler error: copy-constructor unavailable in C
    y = x; //compiler error: assignment operator unavailable in C 
}

MSVC9.0(Visual Studio 2008的C ++编译器)确实生成了默认构造函数但是无法为C生成复制和赋值运算符,尽管C是A的朋友。这是预期的行为还是Microsoft错误?我认为后者就是这种情况,如果我是对的,任何人都可以指向一篇文章/论坛/ ......讨论这个问题或微软对这个问题的反应。提前谢谢。

P.S。顺便说一句,如果BOTH私有继承被更改为受保护,一切正常

P.P.S。我需要一个证据,证明上述代码是合法的或非法的。根据我的理解,确实打算不能从具有虚拟私人基础的类中派生出来。但他们似乎错过了朋友的一部分。所以...在这里,我的第一个赏金:)

4 个答案:

答案 0 :(得分:2)

答案 1 :(得分:1)

具有virtual private base的类不应从C ++ SWG的this派生。编译器正在做正确的事(直到某一点)。问题不在于来自C的A的可见性,而是根本不应该允许C实例化,这意味着该bug是在第一个(默认)构造而不是其他行。

  
      
  1. 具有私有虚拟基类的类是否可以从?
  2. 派生         

    章节:11.2 [class.access.base]
      状态:NAD提交者:Jason   美林日期:未知

class Foo { public: Foo() {}  ~Foo() {} };
class A : virtual private Foo { public: A() {}  ~A() {} };
class Bar : public A { public: Bar() {}  ~Bar() {} }; 
  

~Bar()调用   ~Foo(),由于形成不良   访问违规,对吗? (酒吧的   构造函数有同样的问题,因为   它需要调用Foo的构造函数。)   似乎存在一些分歧   在编译器之间。 Sun,IBM和g ++   拒绝测试用例,EDG和HP接受   它。也许这种情况应该是   通过草案中的说明澄清。在   简而言之,它看起来像一个类   虚拟私有基础无法派生   从

     

理由:这就是预期的目的。

顺便说一下,Visual C ++ v10编译器的行为与问题中提到的相同。从virtualA的继承中删除B可解决问题。

答案 2 :(得分:1)

您的代码可以使用Comeau Online和MinGW g ++ 4.4.1编译。

我提到这只是一个“权威论证”。

从标准POV访问与虚拟继承正交。虚拟继承的唯一问题是它是派生类最多的类,它继承了继承链(或“似乎”)的虚拟派生类。在您的情况下,派生类最多的类具有执行此操作所需的访问权限,因此代码应该编译。

MSVC在虚拟继承方面也存在一些其他问题。

所以,是的,

  • 代码有效,
  • 这是一个MSVC编译器错误。

仅供参考,该错误仍然存​​在于MSVC 10.0中。我找到了一个bug report关于类似的错误,由微软确认。然而,仅仅通过一些粗略的谷歌搜索我找不到这个特殊的错误。

答案 3 :(得分:0)

我认为这不是一个错误。 Just C必须是B的朋友才能复制它的虚拟基类A.