我有一個對象,顯然是雙刪除,儘管是由智能指針跟蹤。我對使用智能指針很陌生,所以我做了一個簡單的函數來測試我是否正確使用對象。共享指針雙刪除
int *a = new int(2);
std::shared_ptr<int> b(a);
std::shared_ptr<int> c(a);
主函數中的這組行導致運行時錯誤,因爲指針超出範圍,爲什麼?智能指針是否應該能夠自己處理刪除操作?
我有一個對象,顯然是雙刪除,儘管是由智能指針跟蹤。我對使用智能指針很陌生,所以我做了一個簡單的函數來測試我是否正確使用對象。共享指針雙刪除
int *a = new int(2);
std::shared_ptr<int> b(a);
std::shared_ptr<int> c(a);
主函數中的這組行導致運行時錯誤,因爲指針超出範圍,爲什麼?智能指針是否應該能夠自己處理刪除操作?
正確的用法是:
std::shared_ptr<int> b = std::make_shared<int>(2);
std::shared_ptr<int> c = b;
一個shared_ptr
預計自己所指向的對象。
你所做的事是創建獨立的智能指針,每一個認爲它有潛在的int
的獨佔所有權。他們不知道彼此的存在,他們不相互交談。因此,當它們超出範圍時,兩個指針都會刪除底層資源,並帶來明顯的結果。
當您創建shared_ptr
時,它會創建一種「管理對象」,它負責資源的生命週期。當您複製 a shared_ptr
時,兩個副本引用相同的管理對象。管理對象會跟蹤多少個shared_ptr
實例指向此資源。一個int*
本身沒有這樣的「管理對象」,因此複製它不會跟蹤引用。
這是你的代碼的最小改寫:
// incidentally, "make_shared" is the best way to do this, but I'll leave your
// original code intact for now.
int *a = new int(2);
std::shared_ptr<int> b(a);
std::shared_ptr<int> c = b;
現在,他們都引用相同的底層管理對象。由於每個shared_ptr
被銷燬,因此int*
上的引用數量會減少,並且最後一個引用也會被刪除。
更好的風格是做std :: shared_ptr
@ h9uest如果這不是對原始問題中提供的代碼的最小修改,那麼您的觀點會更加相關。它從來沒有打算成爲C++的完美例子,也從未聲稱過。如果你閱讀代碼塊中的註釋,你會發現提到了'make_shared'。 – Rook
您只允許從原始指針創建一個智能指針。所有其他共享指針必須是第一個的副本才能正常工作。更妙的是:使用化妝共享:
std::shared_ptr<int> sp1 = std::make_shared<int>(2);
std::shared_ptr<int> sp2 = sp1;
編輯:忘了添加第二個指針
你對自己刪除?你不應該那樣做。使用make_shared而不是手動分配一個。 – Kiroxas