c++學習筆記之類

c++學習筆記系列:http://blog.csdn.net/column/details/17301.html


1、預處理器封套

#ifndef XXX_H
#define XXX_H
...
class xxx{
...
}
...
#endif
如果沒有文件包含此頭文件,XXX_H被定義幷包含這個頭文件;如果已經包含,則不再定義和包含。
爲了防止多次包含同一個頭文件,尤其包含套包含的時候。注意命名要大寫和下劃線

2、對象的sizeof

sizeof一個對象得到的是所有數據成員的大小。
因爲函數不存儲在對象中,而是由編譯器創建獨立於所有對象的函數副本,所有對象共享函數副本

3、訪問對象數據成員和成員函數

對象名或對象引用的情況      a.b          a.b()
對象指針的情況        aPtr -> b           aPtr -> b()

4、工具函數

工具函數即private函數

5、析構函數

~類名()              在對象被撤銷時被調用,某種意義上是與構造函數互補。
class Time{
     Time(...){...}
     ~Time(){...}
}
注意:不接收任何參數,不返回任何參數,void也不行。
          一個類只能有一個析構函數,不允許重載

6、對象傳參

當對象作爲參數或返回值時是傳值參數,即傳的是拷貝
所以當要使用真正對象需要傳引用或指針。

7、const對象\函數

聲明對象(注意位置):void name() const {....}
對象聲明const不能被修改,不能調用非const的成員函數。
成員函數聲明const不能修改對象,同樣不能調用非const的成員函數。
(1)可以對const成員函數進行非const重載。編譯器根據對象性質選擇相應函數,const對象調用const函數;非const對象調用非const函數
(2)構造、析構函數不能聲明const。

8、成員初始化器

int count;
const in num;
Time(int i, int j):count(i),num(j){...}
所有數據成員都可以用成員初始化器來初始化,如上面的形式。
但是const數據成員和引用的數據成員必須使用成員初始化器進行初始化,不能通過賦值初始化。
(1)成員初始化器在構造函數體執行前執行
(2)建議將所有不修改對象的函數聲明爲const。

9、組成

即數據成員是一個其他類的對象。
如果構造函數沒有初始化某個成員,那麼會隱式的調用該成員的默認構造函數。如果該成員的類沒有默認構造函數,編譯報錯

10、friend函數和類(友元)

class A{
     friend class B;
     friend void b(...);
}
友元可以訪問原類中的非public成員和函數。
(1)友元關係不傳遞,不對稱。
(2)友元函數不是成員函數
(3)友元最好在數據成員及函數之前聲明。
(4)友元模板類或模板函數的情況,需要提前定義,否則報錯,如:
template<typename T> class B;
class A{
     friend class<T> B;
}
(5)友元是非模板類的成員函數,也需要提前定義

10、this指針

因爲是指針,所以:this -> x  或  (*this) .x

11、動態內存管理(new\delete)

Time time; 或 int num[24]; 這樣在定義時需要將所有內存分配(所有成員內存或所有元素內存),即使未使用到,且不能改變。
使用動態內存管理實際上是在自由存儲區分配內存區域,通過delete釋放。
Time *timePtr = new Time(....);
delete timePtr;
int *numsPtr = new int[24];
delete [] numsPtr;
(1)釋放時先調用析構函數,再回收內存。數組釋放時不加“[]”只調用第一個元素的析構函數。
(2)不釋放會造成內存泄漏
(3)在編譯時創建數組,大小必須用常量;而動態分配是可以使用任何表達式,如new int[a + b];
(4)動態分配一個對象數組時,會使用對象的默認構造函數初始化
(5)delete之後最好將指針設爲0,如numsPtr=0。因爲回收後內存空間中的信息還在,只是沒有關係了,如果不注意訪問了,會導致極端詭異無法復現的問題
(6)尤其注意循環中要使用new,否則會出錯,如下:
for (int i = 0; i < 5; i++) {
     Node<int> node(i);
     Node<int> *ptr = &node;
}

運行時會發現每次循環ptr指針指向的地址是不變的,也就是說所有的循環一致用一個Node對象而不是每次新建,這樣會導致邏輯錯誤。改成new動態分配後,每次循環都是新的對象。

12、static

static數據成員只能被初始化一次。
int或枚舉類型的const static數據成員可以在類定義中初始化;所有其他類型的數據成員必須在文件作用域(類定義外)定義並初始化。
xxx.h
class{
     ...
private:
     static int a;
     ...
}

xxx.cpp
...
int a = 1;
...

(1)在.cpp文件中定義初始化static數據成員時不能聲明static,應該在.h中聲明爲static
(2)如果成員是對象且有默認構造函數,可以不初始化。
(3)public static數據成員在類外部使用:沒有任何對象時Time::cout;有對象時time.count。
(4)在static函數中不能使用this,否則編譯錯誤。static函數不能被聲明稱const


13、代理類

使用頭文件雖然可以隱藏實現細節,但是依然暴露private數據成員或函數。
使用代理類,只有一個private成員,即被代理類的對象指針。

發佈了106 篇原創文章 · 獲贊 30 · 訪問量 26萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章