日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

智能指针——weak_ptr

發布時間:2024/4/18 编程问答 38 豆豆
生活随笔 收集整理的這篇文章主要介紹了 智能指针——weak_ptr 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

1. 開篇

正式介紹weak_ptr之前,先來復習一下shared_ptr 的一些知識。
我們知道shared_ptr是采用引用計數的智能指針,多個shared_ptr實例可以指向同一個動態對象,并維護了一個共享的引用計數器。

對于引用計數法實現的計數,總是避免不了循環引用(或環形引用)的問題,shared_ptr也不例外。

示例

class Child;class Parent { public:shared_ptr<Child> child;~Parent() { cout << "Bye Parent" << endl; }void hi() const { cout << "He1lo" << endl; } };class Child { public:shared_ptr<Parent> parent;~Child() { cout << "Bye Child" << endl; } };int main() {shared_ptr<Parent> parent = make_shared<Parent>();shared_ptr<Child> child = make_shared<Child>();parent->child = child;child->parent = parent;child- >parent->hi();return 0; }

運行結果

上面代碼的運行結果,只打印出”Hello”,而并沒有打印出"Bye Parent"或"Bye Child",說明Parent和Child的析構函數并沒有調用到。這是因為Parent和Child對象內部,具有各自指向對方的shared_ptr,加上parent和child這兩個shared_ptr,說明每個對象的引用計數都是2。當程序退出時,即使parent和child被銷毀,也僅僅是導致引用計數變為了1,因此并未銷毀arent和Child對象。

parent->child = child; child->parent = parent;


為了解決類似這樣的問題,C++11引入了weak_ptr,來打破這種循環引用。

2. weak_ptr的概念

weak_ptr是為了配合shared_ptr而引入的一種智能指針,它指向一個由 shared_ptr管理的對象而不影響所指對象的生命周期,也就是將一個weak_ptr綁定到一個shared_ptr不會改變shared_ptr的引用計數。

不論是否有weak_ptr指向,一旦最后一個指向對象的shared_ptr被銷毀,對象就會被釋放。

從這個角度看,weak_ptr更像是shared_ptr的一個助手而不是智能指針。

3. weak_ptr的使用

3.1 如何創建weak_ptr實例

當我們創建一個weak_ptr時,需要用一個shared_ptr實例來初始化 weak_ptr,由于是弱共享,weak_ptr的創建并不會影響shared_ptr的引用計數值。

int main() {shared_ptr<int> sp(new int(5));cout <<"創建前sp的引用計數:" << sp.use_count() << endl; //use_count = 1weak_ptr<int> wp(sp);cout <<"創建后sp的引用計數: " << sp.use_count() << endl; //use_count = 1return 0; }

3.2 如何判斷weak_ptr指向對象是否存在

既然weak_ptr并不改變其所共享的shared_ptr實例的引用計數,那就可能存在weak_ptr指向的對象被釋放掉這種情況。

這時,我們就不能使用weak_ptr直接訪問對象。那么我們如何判斷weak_ptr指向對象是否存在呢?
C++中提供了lock函數來實現該功能。
如果對象存在,lock()函數返回一個指向共享對象的shared_ptr,否則返回一個空shared_ptr。

class Object { private:int value; public:object(int x = 0) :value(x) { cout << "object Constructor.. ." << endl; }~object() { cout << "object Destructor..." <<endl; }int Getvalue() const { return value; } }; int main() {shared_ptr<Object> sp(new Object(10));weak_ptr<Object> wp(sp);//sp.reset(); //??if (shared_ptr<Object> pa = wp.lock()){cout << pa->GetValue() << endl;}else{//weak_ptr還提供了expired()函數來判斷所指對象是否已經被銷毀cout << wp.expired() << endl;cout << "wp引用的對象為空" <<endl;}return 0; }

3.3 如何使用weak_ptr

weak_ptr并沒有重載operator->和operator*操作符,因此不可直接通過weak_ptr使用對象,典型的用法是調用其lock函數來獲得shared_ptr示例,進而訪問原始對象。

使用weak_ptr來改造最前面的代碼,打破循環引用問題。

class Child;class Parent { public:weak_ptr<Child> child; //~parent() { cout << "Bye Parent" <<endl; }void hi() const { cout<< "Hello" << endl; } };class Child { public:weak_ptr<Parent> parent; //~Child() { cout << "Bye Child" << endl; } };int main() {shared_ptr<Parent> parent = make_shared<Parent>();shared_ptr<Child> child = make_shared<Child>();parent->child = child;child->parent = parent;//child->parent->hi(); //??if(child->expired()) { child->parent.lock()->hi(); }return 0; }

總結

以上是生活随笔為你收集整理的智能指针——weak_ptr的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。