【问题标题】:Need an example showing that default constructor is not inherited需要一个示例显示默认构造函数没有被继承
【发布时间】:2014-06-08 12:57:33
【问题描述】:

我知道默认构造函数不是继承的,如n3337 中所述。

还有一个例子:

struct B2 {
  B2(int = 13, int = 42);
};

struct D2 : B2 {
  using B2::B2;
};

解释得很好:

D2B2 的候选继承构造函数集是

...
—B2(int = 13, int = 42)
—B2(int = 13)
—B2()

最重要的是:

D2 中存在的构造函数集是
—D2(),隐式声明的默认构造函数,不继承

对我来说,这个例子并没有显示出区别,从某种意义上说,即使这个构造函数是被继承的——它的行为与隐式声明的默认构造函数并没有什么不同。

我需要一个示例,以让熟悉 C++03 但想学习 C++11 的观众易于理解。


[更新]
所有答案(包括我自己的)都是“如果默认 c-tor 被继承,那么示例将编译/不编译”。

我更喜欢结果(可观察到的行为)与其他情况不同的答案。

【问题讨论】:

    标签: c++ inheritance c++11 default-constructor inherited-constructors


    【解决方案1】:

    一个可能的区别:具有默认构造函数的类的多构造函数继承。例如:

    struct A { A(int=0); };
    struct B { B(double=3.14); };
    struct C : A, B {
      using A::A;
      using B::B;
    };
    
    C c;
    

    如果继承了默认构造函数,C 将从AB 中继承一个,从而导致歧义。

    我想不出多构造函数继承的用例,所以这可能不是您正在寻找的完美示例,但它确实是。

    【讨论】:

      【解决方案2】:

      考虑:

      struct foo
      {
          foo() {}
          foo(int) {}
      };
      
      struct bar : foo
      {
          using foo::foo;
      };
      
      int main()
      {
          bar b;
      }
      

      这样编译:由于bar没有用户声明的构造函数,默认构造函数将被隐式声明。

      struct foo
      {
          foo() {}
          foo(int) {}
      };
      
      struct bar : foo
      {
          using foo::foo;
          bar(double) {}
      };
      
      int main()
      {
          bar b;
      }
      

      这不会编译。默认构造函数不是继承的,也不是隐式声明的,因为有bar(double)构造函数。

      【讨论】:

      • 查看提案(例如N2203),这似乎是(部分?)不继承复制/移动和默认ctors的理由。
      【解决方案3】:

      这是一个例子,它可以从继承构造函数的以下特性中产生:

      12.9 继承构造函数
      [...]
      4) 如此声明的构造函数与 X 中相应的构造函数具有相同的访问权限。

      所以我的建议是在基础中保护默认构造函数:

      class Base {
      protected:
          Base(int) {}
          Base() = default;
      };
      

      如果此构造函数是派生的,则无法实例化派生类,因为派生构造函数将具有受保护的访问权限。如果不是派生的 - 那么默认隐式声明的构造函数具有公共访问权限:

      struct Derived : Base {
          using Base::Base;
      };
      
      int main() {
          Derived d1{};  // not inherited, default constructor is public
          Derived d2{1}; // not compiling since this c-tor is inherited, thus protected
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-10-04
        • 2016-03-24
        • 2015-07-09
        • 2011-05-20
        • 1970-01-01
        • 2011-04-12
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多