C++類的構造函數


一,關於構造函數

作用:初始化類的成員變量,所以當創建類對象或者類對象被創建就會調用構造函數

特點:

  1. 函數名和類名一樣,且沒有返回值
  2. 當沒有顯式的定義構造函數時,系統會自己生成默認的構造函數
  3. 構造函數可以重載

二,構造函數的幾種表現形式

2.1 默認的構造函數

Test1.cpp

 1 #include "test1.h"
 2 
 3 Test1::Test1()
 4 {
 5     cout<< "Test1 construction" << endl;
 6 }
 7 
 8 Test1::~Test1()
 9 {
10     cout<< "~Test1 destructor" << endl;
11 }
12 
13 void Test1::getInfo()
14 {
15     cout << "get: year: " << m_year << " month: " << m_month << " day: " << m_day << endl;
16 }

 

 

Test1.h

#ifndef TEST1_H
#define TEST1_H
#include <iostream>
using namespace std;

class Test1
{
public:
    Test1();//默認構造函數
    ~Test1();//析構函數
    void getInfo();
private:
    int m_year;
    int m_month;
    int m_day;
};

#endif // TEST1_H

 

2.2 自定義的構造函數

Test2.cpp

 1 /*
 2  * Test2
 3 */
 4 Test2::Test2()
 5 {
 6     cout<< "Test2 default construction" << endl;
 7 }
 8 Test2::Test2(int year, int month, int day)
 9 {
10     m_year = year;
11     m_month = month;
12     m_day = day;
13     cout<< "Test2 construction" << endl;
14 }
15 
16 Test2::~Test2()
17 {
18     cout<< "~Test2 destructor" << endl;
19 }
20 
21 void Test2::getInfo()
22 {
23     cout << "get: year: " << m_year << " month: " << m_month << " day: " << m_day << endl;
24 }

 

Test2.h

 1 class Test2
 2 {
 3 public:
 4     Test2();//默認構造函數
 5     Test2(int year=19, int month=4, int day=15);//帶有默認參數的構造函數
 6     ~Test2();//析構函數
 7     void getInfo();
 8 private:
 9     int m_year;
10     int m_month;
11     int m_day;
12 };

 

 

注意事項:

注意使用默認參數時,有可能出現重復定義的構造函數

 1 //測試用例1
 2 Test2 t21;//錯誤的使用,重復的構建函數
 3 t21.getInfo();
 4 
 5 //錯誤信息
 6 /*
 7 D:\QT_project\test\Test\main.cpp:21: error: C2668: 'Test2::Test2' : ambiguous call to overloaded function
 8 d:\qt_project\test\test\test1.h(23): could be 'Test2::Test2(int,int,int)'
 9 d:\qt_project\test\test\test1.h(22): or       'Test2::Test2(void)'
10 while trying to match the argument list '()'
11 */
12 
13 //測試用例2  
14 Test2 t22(1,2);//正確的用法
15 t22.getInfo();

 

2.3 初始化列表

注意事項1:

初始化列表的賦值時刻和函數體內賦值是不同的,初始化列表是在對象創建成功之前完成的,而函數體內賦值是在對象成員創建成功后進行賦值操作。

必須使用初始化列表的幾種場景:

  1. 成員是const類型或者是引用類型
  2. 有一個成員是類類型的對象(且沒有缺省的構造函數)

Test3.cpp

 1 /*
 2  * Test3
 3 */
 4 
 5 Test3::~Test3()
 6 {
 7     cout<< "~Test3 destructor" << endl;
 8 }
 9 
10 void Test3::getInfo()
11 {
12     cout << "get: year: " << m_year << " month: " << m_month << " day: " << m_day << endl;
13 }

 

Test3.h

 1 class Test3
 2 {
 3 public:
 4     //Test3();//默認構造函數  當前成員變量有const類型,且沒有初始化,因此無法使用默認的構造函數
 5     Test3(int year, int month, int day)
 6         :m_year(year),m_month(month),m_day(day)//初始化列表
 7     {}
 8     Test3(int year=19, int month=4);
 9     ~Test3();//析構函數
10     void getInfo();
11 private:
12     int m_year;
13     int m_month;
14     int const m_day;
15 };

 

main.cpp

1 Test3 t3(19,4,15);
2 t3.getInfo();

 

關於1,因為對於const和引用類型必須要進行初始化,所以必須在初始化列表中進行初始化

關於2,當類類型成員有缺省的構造函數時,在創建對象的時候系統會默認調用,因為不用傳參。但是當你的構造函數不是缺省的,如果不在初始化列表中進行調用構造函數,系統就無法知道怎么調用類類型成員的構造函數,那么就無法創建。

 1 class Time
 2 {
 3 public:
 4     Time(int h)
 5     {
 6         m_hour = h;
 7     }
 8 private:
 9     int m_hour;
10 };
11 
12 class Test3
13 {
14 public:
15     Test3(int year, int month, int day)
16         :m_year(year),m_month(month),m_day(day), t(10)//初始化列表
17     {}
18     ~Test3();//析構函數
19     void getInfo();
20 private:
21     int m_year;
22     int m_month;
23     int const m_day;
24     Time t;
25 };

 

注意事項2:

成員初始化順序:初始化列表的順序並不限定初始化的執行循序。成員的初始化順序是與類中定義的的順序保持一致。

<文檔結束>

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM