1. 程式人生 > >類中默認的函數

類中默認的函數

delet 當我 運行 對象 span 返回 this 刪除 進行

我們自己定義的類,或者C++標準裏默認提供的類,我們都可以看成是區別於基本數據類型(char,int,double等)的新類型,比如我們使用int類型時,一般會有如下的一些操作,如:

  (1)int a;//定義一個變量

  (2)int a = 10;//定義一個變量並進行初始化操作

  (3)

    int a(10);

    int b = a;//定義一個變量,並對其進行初始化操作

  (4)

  void fun(int i){}

  int a = 10;

  fun(a);//定義一個變量並將其作為函數參數進行傳遞,函數參數的給值也是初始化操作

既然都是數據類型,那麽其操作也是大同小異的。在一個沒有任何成員函數的類,會有以下的默認函數(對於這些默認的函數,只要自己手動編寫了這些函數,那麽默認的就會被覆蓋):

class Test
{
public:
    Test() {}//默認構造函數
    Test(const Test &t) {}//默認拷貝構造函數
    Test &operator=(const Test &t) {}//默認“=”運算符重載函數
    ~Test() {}//默認析構函數
};

  (a)默認無參構造函數(只要是構造函數,都沒有返回值的)

    作用是讓這個新的數據類型可以定義變量(對象),就像int a;

    此時,我們不能完成成員變量的初始化,要想完成成員變量的初始化,我們可以自己寫一個構造函數,然後再初始化列表中進行成員變量的初始化(註意:初始化列表的執行順序是從上到下,即成員變量的聲明順序)

  (b)默認拷貝構造函數

    參數是當前類的一個常量引用

    默認的拷貝構造是淺拷貝,當有成員變量時,淺拷貝時這樣的:

class Test
{
public:
    int m_a;
public:
    Test() {}
    Test(const Test &t)
    {
        this->m_a = t.m_a;
    }
    Test &operator=(const Test &t) {}
    ~Test() {}
};

對於這種類型的變量時沒問題的,但是當成員變量是其他類的指針變量時,那麽就會讓兩個指針變量指向同一塊空間,當我們用delete 指針變量時,就會刪除同一塊空間刪除兩次,這樣就會導致程序奔潰,所以這種情況,我們需要自己手動編寫拷貝構造函數,將那塊空間也拷貝一份,這樣程序就能正常運行了。

class Test{};

void fun(Test t);
Test fun2();

Test t1;
Test t2(t1);//調用默認的拷貝構造
Test t3 = t1;//調用默認的拷貝構造 這個和上面是一樣的,只是寫法不同
Test t4;
fun(t1);//調用默認的拷貝構造
t4 = fun2();//調用默認的拷貝構造

  (c)默認“=”運算符重載函數

class Test{};

Test t1;
Test t2;
t2 = t1;//調用默認“=”操作符重載函數

  註意:默認拷貝構造函數和默認“=”操作符重載函數都會檢查對象是否初始化,比如:

class Test
{
public:
    int m_a;
};

int main()
{
    Test t1;
    Test t2;
    t2 = t1;//編譯失敗,使用了未初始化的局部變量"t1"
    Test t3 = t1;//編譯失敗,使用了未初始化的局部變量"t1"

    return 0;
}

  (d)析構函數

類中默認的函數