条款05:了解C++默默编写并调用哪些函数

        什么时候empty class(空类)不再是个empty class呢?当C++处理过它之后。是的,如果你自己没声明,编译器就会为它声明(编译器版本的)一个copy构造函数、一个copy assignment操作符和一个析构函数。此外如果没有声明任何构造函数,编译器也会为你声明一个default构造函数。所有这些函数都是public且inline(见条款30).因此,如果你写下:

        class Empty {};

这就好像你写下这样的代码:

class Empty {
public:
    Empty(){...}                              // default构造函数
    Empty(const Empty& rhs) {...}             // copy构造函数
    Empty& operator=(const Empty& rhs) {...}  // copy assignment 操作符
    ~Empty() {...}                            // 析构函数
};

       唯有当这些函数被需要(被调用),它们才会被编译器创建出来。程序中需要它们是很平常的事。下面代码造成上述每一个函数被编译器产出:

Empty e1;      // default构造函数
               // 析构函数
Empty e2(e1);  // copy 构造函数
e2 = e1;       // copy assignment操作符

        default构造函数和析构函数主要是给编译器一个地方用来放置“藏身幕后”的代码,像是调用base classes和non-static成员变量的构造函数和析构函数。注意,编译器产出的析构函数是个non-virutal(见条款7),除非这个class的base class自身声明有virtual析构函数(这种情况下这个函数的虚属性virtualness主要来自base class)。

       至于copy构造函数和copy assignment操作符,编译器创建的版本只是单纯地将来源对象的每一个non-static成员变量拷贝到目标对象。

        编译器默认生成的函数前提是用户没有自己声明,如果自己声明了构造函数、copy构造函数、copy assignment操作符则编译器就不会生成默认函数来覆盖你之前的声明了。这里注意,析构函数不管你自己声不声明,系统都会执行一个默认析构函数。

        另外注意copy assignment操作符遇到特殊情况时将会拒绝生成对应函数。如果成员变量是引用类型或者有const修饰,则默认赋值操作符会拒绝生成,因为引用和const都是不可改动的,所以需要用户自定义赋值操作符。

   请记住

  • 编译器可以暗自为class创建default构造函数、copy构造函数、copy assignment操作符,以及析构函数。

发布了88 篇原创文章 · 获赞 17 · 访问量 7万+

猜你喜欢

转载自blog.csdn.net/yj_android_develop/article/details/94361153