在咱們學習C++的過程當中,咱們不免會遇到類,在類中有6個默認的函數,它們分別爲:構造函數、拷貝構造函數、析構函數、賦值操做符重載、取地址操做符重載和const修飾的取地址操做符重載。函數
一、什麼是拷貝構造函數:學習
只有單個形參,並且該形參是對本類類型對象的引用(經常使用const修飾),這樣的構造函數稱爲拷貝構造函數。拷貝構造函數是特殊的構造函數,建立對象時使用已存在的同類對象來進行初始化,由編譯器自動調用。優化
class CDate { public: CDate() {} CDate(const int year, const int month, const int day) { _iYear = year; _iMonth = month; _iDay = day; } CDate(const CDate& date) //拷貝構造函數 { _iYear = date._iYear; _iMonth = date._iMonth; _iDay = date._iDay; } private: int _iYear; int _iMonth; int _iDay; };
一、它是構造函數的重載。this
二、它的參數必須使用同類型對象的引用傳遞。指針
三、若是沒有顯式定義,系統會自動合成一個默認的拷貝構造函數。默認的拷貝構造函數會依次拷貝類的數據成員完成初始化。code
將d1的內容拷貝到d2中:對象
void FunTest() { CDate d1(1990, 10, 1); CDate d2(d1);//將d1的內容拷貝到d2中 d1.print(); d2.print(); }
傳值方式做爲函數的參數:遞歸
void FunTest(const CDate date) { CDate d2(date); d2.print(); }
三、傳值方式做爲函數返值:生命週期
CDate FunTest() { CDate date(1996,3,10); return date; } int main() { CDate d1= FunTest(); d1.print(); return 0; }
一、什麼是析構函數: 析構函數:與構造函數功能相反,在對象被銷燬時,由編譯器自動調用,完成類的一些資源清理和汕尾工做。ci
class CArray { public: CArray(size_t capacity) : _capacity(capacity) { _pData = (int*)malloc(capacity*sizeof (int)); _size = 0; } ~CArray() //析構函數 { if (NULL != _pData) { free(_pData); _pData = NULL; } _size = 0; _capacity = 0; } private: int* _pData; size_t _size; size_t _capacity; };
一、析構函數在類名前(即構造函數名)加上字符~。 二、析構函數無參數無返回值。 三、一個類有且只有一個析構函數。若未顯示定義,系統會自動生成缺省的析構函數。 四、對象生命週期結束時,C++編譯系統系統自動調用析構函數。 五、注意析構函數體內並非刪除對象,而是作一些清理工做。
賦值運算符重載在C++中分兩種狀況,一是用static修飾的靜態成員變量或者是靜態成員函數,二是用const修飾的常成員變量或常成員函數。 ###static關鍵字 static修飾的變量
static int a;
static修飾的函數
static int FunTest() {}
聲明爲static的類成員(成員數據或成員函數)稱爲類的靜態成 員
一、靜態成員爲全部類對象所共享,不屬於某個具體的實例。 二、類靜態成員便可用類名::靜態成員或者對象.靜態成員來訪問。 三、類靜態成員變量必須在類外定義,定義時不添加static關鍵字。 四、類的靜態成員函數沒有默認的this指針,所以在它裏面不能使用任何非靜態成員。 五、靜態成員和類的普通成員同樣,也有public、protected、private3種訪問級別,也能夠具備返回值,const修飾符等參數。
一、非靜態的成員函數能夠調非靜態的變量。 二、非靜態的成員函數能夠調靜態的變量。 三、靜態函數能夠調用靜態變量。 四、靜態函數不能夠調用非靜態變量。
const修飾的變量
const int a; const int const a;
const修飾的函數
int FunTest() const {} const int FunTest() const {}
const使用場景: 一、const修飾形參,通常和引用同時使用。 二、const修飾返回值。 三、const修飾類數據成員,必須在構造函數的初始化列表中初始化。 四、const修飾類成員函數,實際修飾隱含的this,表示在類中不能夠對類的任何成員進行修改。 五、在const修飾的成員函數中要對類的某個數據成員進行修改,該數據成員定義聲明是必須加mutable關鍵字。
一、非const對象能夠調用非const成員函數和const成員函數。 二、const對象能夠調用const成員函數,但不能夠調用非const成員函數和。 三、非const成員函數內能夠調用其它的const成員函數和非const成 員函數。 四、const成員函數內不能夠調用其它的const成員函數和非const成員 函數。
class CTest { public: CTest* operator&() { return this; } const CTest* operator &()const { return this; } };
以inline修飾的函數叫作內聯函數,編譯時C++編譯器會在調用內聯函數的地方展開,沒有函數壓棧的開銷,內聯函數提高程序運行的效率。
一、inline是一種以空間換時間的作法,省去調用函數額開銷。因此代碼很長或者有循環/遞歸的的函數不適宜使用內聯。 二、inline對於編譯器而言只是一個建議,編譯器會自動優化,若是定義爲inline的函數體內有循環/遞歸等等,編譯器優化時會忽略掉內聯。 三、inline必須函數定義放在一塊兒,才能成爲內聯函數,僅將inline放在聲明前是不起做用的。 四、定義在類內的成員函數默認定義爲內聯函數。
class Date { public: void Func() // 定義在類內部默認爲內聯函數 {} void Display(); private: int _year; // 年 int _month; // 月 int _day; // 日 }; inline void Date::Display() // 成員函數定義爲內聯 { cout << "year:" << _year << endl; cout << "month:" << _month << endl; cout << "day:" << _day << endl; } inline void Test() // 全局函數定義爲內聯 {}