C++类和对象:默认成员函数(1)

构造函数

<1>定义:用来初始化已经实例化的对象的函数,由编译器默认生成,对象实例化时会自动调用它。

<2>对不同类型的处理方式:对内置类型(int,double,指针等)不作处理,具体看编译器。对自定义类型会自动生成默认构造函数。(注意:当我们显示实现构造时,编译器就不会再自动生成默认构造了)

<3>什么时候需要显示实现默认构造呢?两种情况:1.必须需要我们手动开辟空间的情况(比如需要在堆上开空间的,像是栈,链表之类的)2.自定义类型没有默认构造的时候,比如下面这种情况

class B
{
public:
    B(int n)//显示实现了B的构造,编译器将不会再生成B的默认构造
    :_a(n)
    {}
private:
    int _a;
};

class A
{
    B _b;//这种情况A就要显示实现构造,
         //因为B没有默认构造可以调用,需要手动去调B的构造
};

<4>如何自己写构造:第一种用初始化列表,函数名与类名相同,没有返回值,格式--> 类名+(参数)+ “ :”+{ } ,成员变量定义在冒号后面,用逗号分隔。第二种就是在声明的位置给缺省值,其实本质也是初始化列表用这个缺省值进行初始化。一般建议只用其中一种,不要混用。(注意:初始化顺序与声明顺序相同,建议二者顺序保持一致),总结如下

下面演示显示实现一个日期类的初始化列表:

class Date
{
public:
   Date(int& x, int n= 1,)//初始化列表(第一种方法)
    :_a(x),
     _b(n)
   {
     //若无其他要求函数体可为空
   } 
private:
   int& _a;    
   const int _b;//可给缺省值-->const int _b=1;(第二种方法)
};

析构函数

<1>定义:用来销毁已经实例化的对象的函数,由编译器默认生成,对象生命周期结束时会自动调用它。

<2>对不同类型的处理方式:对内置类型不作处理,具体看编译器。对自定义类型会自动生成默认构造函数。不管是内置类型还是自定义类型,只要是在堆上开辟的就需要显示实现析构,在其他区(比如静态区,栈,常量区)就不用,因为只有堆上开辟的需要我们手动释放,否则会有空间泄露问题。

<3>如何自己写构造:函数名与类名相同,没有返回值,格式--> “~”+类名+(参数)+ “ :”+{ } ,以数据结构-栈为例显示实现析构:

class stack
{
public:
   ~Stack()//栈的析构
   {
      free(_a);
      _a = nullptr;
      _top = _capacity = 0;
    }
private:
    STDataType* _a;
    size_t _capacity;
    size_t _top;
};

构造与析构的顺序问题

1.全局对象先于局部对象进行构造,局部对象按照出现的顺序进行构造,无论是否为static

2.类的析构函数调用一般按照构造函数调用的相反顺序进行调用。局部变量出函数就析构,但是要注意static对象的存在, 因为static改变了对象的生存作用域,需要等待程序结束时才会析构释放对象,顺序在全局对象的析构之前。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值