c++ 类构建对象

xiaoxiao2021-02-28  75

我将c++ 类构建对象的方式分为两类:

1、显示调用构造函数,构造对象如:

            class A{

public:

A() //默认的无参构造函数

{}

A(int)

{}

A(const A& )  //拷贝构造函数,如果不定义,则使用编译器自己生成的拷贝构造函数(为浅拷贝)

{}

};

A  a(56); //显示调用带int参数的构造函数

A  a1(a); //显示调用拷贝构造函数

2、通过带一个参数的构造函数具有隐式转换功能,来调用构造函数,初始化对象。

 

     class A{

public:

A() //默认的无参构造函数

{}

A(int)

{}

A(const A& )  //拷贝构造函数,如果不定义,则使用编译器自己生成的拷贝构造函数(为浅拷贝)

{}

};

A a = 5; // 5是int型,并不是class A 类型.由于带一个参数的构造函数具有隐式转换功能,所以,编译器会将int型的5转换成临时对象A(5)来构造对象a;

A b = a; //a是class A 类型,编译器将会调用A(a)生成临时对象来构造b;

 

附加:使用临时的无名对象来构造新对象时,并不会调用拷贝构造函数,而是将旧的临时的无名对象换成新的有名对象。这样做可以加长临时对象的生存期。

 

     注意:如果构造函数里加上explicit 修饰了,则该构造函数只能显示调用,不具备隐式转换的功能。

另外:c++里构造函数不能用static或virtual关键字进行修饰

为什么不能用virtual修饰?

因为执行虚函数时,会通过指向虚函数表的指针(vptr)调用表中的虚函数,而虚函数表只有在对象构建成功后,该类含有虚函数则会存在虚函数表。

所以,如果用virtual修饰构造函数,那么此时,对象都没有构造成功,虚函数表都不存在。也就不能调用虚方法。所以构造函数不能用virtual修饰

vptr指针指向虚函数表,执行虚函数的时候,会调用vptr指针变量指向的虚函数表中的虚函数。 当定义个对象的时候,首先会分配内存空间,然后再执行构造函数对该对象进行初始化构造。vptr变量是在构造函数中进行初始化的。又因为要想执行虚函数必须通过vptr变量找到虚函数表。

 

     class A{

public:

A()

{}

explicit A(int)

{}

explicit A(const A& ) 

{}

};

此时, A a ;//正确

   A b(5); //正确

A c(a); //正确    均显示调用构造函数

但是      A d = a;//则,编译错误,找不到匹配的构造函数。

A e = 5 ; //错误;

 

什么时候调用拷贝构造函数,和调用=(赋值运算符)方法?

拷贝构造函数也是构造函数;1.在构造对象时,调用;2.拷贝构造函数是带一个参数的构造函数具有隐式转化功能,在需要隐式转化时,会调用。

调用赋值运算符(=)只有在赋值时才会使用。只有数据类型相同,或者数据类型能隐式转化,或者重载了赋值运算符的情况下才能使用正常。

下面是例子:

class student

{

public:

          int sno;

          student (int sno):sno(sno)

         {}

        student(const student& s)

       {

             printf("aaaaaaaaaaaaa\n");

      }

        ~student()

       {}

     /*

     void operator=(int a)

     {

          sno=a;

    }

   */

};

 

int main()

{

       student s=10;//由于有带一个int参数的构造函数,先将10隐式转化成student(10)临时无名对象,在使用临时无名对象初始化对象;(就是将临时的无名的对象换成新的有名的对象)

       s=100;//如果没用重载赋值运算符,就会先调用构造函数student(100),生成临时无名对象(此时数据类型相同),再赋值。

     //上面是重载=运算符了,就直接调用重载的=运算符     

       return 0;

}

注意:构造函数也可以用private、protected、public修饰和普通方法用他们修饰一样

private修饰构造函数,只允许在类里使用该构造函数即(只能在类里构造对象,单例模式)

protected修饰构造函数,允许在类里和派生类中使用,如:

class A { protected: A() { printf("aaa\n"); } }; class B:public A { public: B() { printf("bbbb\n"); } };

class C:public A{public: C():A(){printf("CCCC\n");}};

public修饰则可以在类外和派生类或者类里使用

转载请注明原文地址: https://www.6miu.com/read-83997.html

最新回复(0)