c 11學習筆記

2022-09-23 09:24:11 字數 2856 閱讀 7850

c++ 98的 std::auto_ptr已經被徹底遺棄了,取而代之的是unique_ptr、shared_ptr與weak_ptr。大部分時候我們自己手動申請記憶體方式記憶體都是沒有問題的,問題是如果程式很大了之後,乙個複雜的物件,多次拷貝的代價非常高,很多地方都會使用到,只存在乙份拷貝顯然是最好的,這個時候物件生命週期的管理就會很複雜,所以c++引入了智慧型指標。  

任何事物都會有兩面性。  

shared_ptr

摘錄於effective c++, 3rd edition, item 17: 在 standalone statements(獨立語句)中將 new 出來的 objects(物件)存入 smart pointers(智慧型指標)比如 

複製**

class widget

;~widget()

;}; 

int priority()

void processwidget(int priority,std::shared_ptr pw)

int main()

複製**

processwidget執行的過程應該是

1.     new widget

2.           shared_ptr constructor

3.         priority()

我在llvm上測試的結果也是這個執行順序

也許某些編譯器上可能執行的順序是

new widget

priority() //發生異常

shared_ptr constructor

就有可能有記憶體洩露  

所以最好的辦法還是應該把new widget提到外面來寫,所以好的編碼習慣很重要。  

2.迴圈引用

複製**

#include

using namespace std;

class a;

class b;

typedef std::shared_ptr aptr;

typedef std::shared_ptrbptr;

class a }; 

class b }; 

int main ()

複製**

要解決這個問題就需要引入乙個弱引用的智慧型指標了weak_ptr

複製**

class a;

class b;

typedef std::shared_ptr aptr;

typedef std::shared_ptrbptr;

typedef std::weak_ptr aweakptr;

typedef std::weak_ptrbweakptr;

class a

}; class b

}; int main ()

複製**

這兩種指標其實和oc裡面的 strong, weak非常相識。  

weak_ptr的另外一種用法

使用情景:當類物件被 shared_ptr 管理時,需要在類自己定義的函式裡把當前類物件作為引數傳給其他函式時,這時需要傳遞乙個 shared_ptr ,否則就不能保持 shared_ptr 管理這個類物件的語義(因為有乙個 raw pointer 指向這個類物件,而 shared_ptr 對類物件的這個引用沒有計數,很有可能 shared_ptr 已經把類物件資源釋放了,而那個呼叫函式還在使用類物件——顯然,這肯定會產生錯誤)。《摘錄:  

直接看官網的例子吧:

《  複製**

#include

#include

struct good: std::enable_shared_from_this}; 

struct bad

~bad() }; 

class cobj: public std::enable_shared_from_this   // 只有cobjmgr可以建立與刪除

~cobj(){}}; 

int main()

// ub: double-delete of bad

複製**

1.絕對不能在建構函式中呼叫shared_from_this()

因為shared_ptr裡面初始化enable_shared_from_this的成員weak_ptr,      這個時候weak_ptr還是空值。   

2.為什麼內部不能用this指標

因為我們程式中用shared_ptr來管理指標,如果我們在類的內部傳遞的過程中用原始指標,這樣類內部的引用shared_ptr不會察覺到,因為有可能我們傳進去的時候已經被shared_ptr釋放掉了。  

unique_ptr

相對就要單純許多了,unique_ptr「唯一」擁有其所指物件,只能有乙個unique_ptr指向給定物件(通過禁止拷貝語義、只有移動語義來實現)。  

代替普通指標

複製**

void foo()    

unique_ptr px(new x);  

複製**

在函式中返回物件  

unique_ptr foo()  

放入容器中

vector> vs , new string,new string  };  

vector>v;  

unique_ptr test(new string("11111"));  

v.push_back(std::move(test));//使用移動語法

支援直接持有陣列

std::shared_ptr p(new int[10],

(int* p));

//或者使用helper

std::shared_ptr p(new int[10],std::default_delete());

C 11學習筆記 Type Support

其實主要還是對c 的std庫的學習吧,雖然用的不少但是對c 的全貌還不太了解。主要包括3個部分 基本型別 rtti 萃取技術 traits size t 用的太多了,不說了。ptrdiff t 乙個有符號的型別,通常用來表示兩個指標相減的結果,是乙個機器相關的型別。和size t不同的是,size ...

C 11學習筆記 五

指標空值 nullptr include using namespace std void f char c void f int i int main 本程式中,null被定義為0,這裡引發錯誤的原因是 c 98中,0既可以是乙個整形,也可以是乙個 void 指標。如果想要呼叫f char c 版...

C 11學習筆記二

用處 基類擁有眾多建構函式而派生類只有一些成員函式 資料不多 時,可以直接繼承基類建構函式而不必重寫。用法 class base class derive base 注意 如果派生類有多個基類時有可能導致衝突,解決辦法是派生類顯示定義該建構函式 用處 一些建構函式需要呼叫相同的 類似的 段時,可將該...