• c++类大四个默认函数-构造函数 析构函数 拷贝构造函数 赋值构造函数


      每个类只有一个析构函数和一个赋值函数,但可以有多个构造函数(包含一个拷贝构造函数,其它的称为普通构造函数)。对于任意一个类A,如果不编写上述函数,C++编译器将自动为A 产生四个缺省的函数,例如:

      A(void);//缺省的无参数构造函数

      A(const A&a);//缺省的拷贝构造函数

      ~A();//缺省的析构函数

      A&operator=(const A &a);//缺省的赋值构造函数

    1)、“缺省的拷贝构造函数”和“缺省的赋值函数”均采用“位拷贝”而非“值拷贝”的方式来实现,倘若类中含有指针变量,这两个函数注定将出错。

    2)、当类还没有生成的时候,调用大是拷贝构造函数,当类已经生成的时候,调用的是赋值构造函数,如下所示:

      A a;

      A b;

      b = a;//此时类a和b都已经生成了,所以调用的是赋值构造函数

      A c;

      A d=c;//此时类d还没有生成,所以调用的是拷贝构造函数

    3)、所有的函数调用传参数,调用的都是拷贝构造函数。如果函数参数用的是引用类型,则不会发生参数的拷贝,也就不会调用任何函数了。

    如下:

      void print_a(const A a);//调用拷贝构造函数

      void print_b(const A &a);//为引用,不会调用任何函数

    4)、拷贝构造函数和赋值构造函数对实现。

      A::A(const A&a)

      {

      }

      拷贝构造函数没有返回,为一个全新的类。

      A &A::operator=(const A&a)

      {

        return *this;

      }

      赋值构造函数返回自身,即*this,为在原先的类上大操作。

    explicit:explicit构造函数是用来防止隐式转换的。

      C++提供了关键字explicit,声明为explicit的构造函数不能在隐式转换中使用

      C++中, 一个参数的构造函数(或者除了第一个参数外其余参数都有默认值的多参构造函数), 承担了两个角色。 1、是个构造器 ,2 是个默认且隐含的类型转换操作符
    所以, 有时候在我们写下如 AAA = XXX, 这样的代码, 且恰好XXX的类型正好是AAA单参数构造器的参数类型, 这时候编译器就自动调用这个构造器, 创建一个AAA的对象。
    这样看起来好象很酷, 很方便。 但在某些情况下(见下面权威的例子), 却违背了我们(程序员)的本意。 这时候就要在这个构造器前面加上explicit修饰, 指定这个构造器只能被明确的调用/使用, 不能作为类型转换操作符被隐含的使用。
      
    class Test1
    {
    public:
        Test1(int n)
        {
            num=n;
        }//普通构造函数
    private:
        int num;
    };
    class Test2
    {
    public:
        explicit Test2(int n)
        {
            num=n;
        }//explicit(显式)构造函数
    private:
        int num;
    };
    int main()
    {
        Test1 t1=12;//隐式调用其构造函数,成功
        Test2 t2=12;//编译错误,不能隐式调用其构造函数
        Test2 t2(12);//显式调用成功
        return 0;
    }
      Test1的构造函数带一个int型的参数,Test1 t1 = 12会隐式转换成调用Test1的这个构造函数。而Test2的构造函数被声明为explicit(显式),这表示不能通过隐式转换来调用这个构造函数,因此Test2 t2 = 12会出现编译错误。
          普通构造函数能够被隐式调用。而explicit构造函数只能被显式调用。
  • 相关阅读:
    【解决】client does not support authentication
    DesktopLayer.exe专杀
    SVN客户端操作(clean up|commit|update)系统找不到指定的文件
    怎样判断一个exe可执行程序(dll文件)是32位的还是64位的
    Windows 调用OpenProcess失败
    win10 请求操作需要提升解决方案
    LINUX下C++编程如何获得某进程的ID
    GitHub
    Git分支管理
    Gi命令行操作
  • 原文地址:https://www.cnblogs.com/renyuan/p/6524316.html
Copyright © 2020-2023  润新知