所以,據我所知,你可以通過返回指針來返回C++中的對象。但我的印象是,一旦函數完成運行,析構函數就會被所有的對象調用。爲什麼析構函數不會調用你要返回的對象?爲什麼析構函數不會在你要返回的對象上調用?
0
A
回答
5
對象只與自動存儲時間析構函數時,這些對象離開其範圍被稱爲(不只是一個功能,但任何範圍:牙套,for
-statements,甚至單行表達式)。
在另一方面,靜態存儲持續時間的對象僅破壞在程序退出,並且動態存儲持續時間的對象(即具有new
操作者創建的那些)僅僅手動獲得銷燬您請求。
當您按照您所描述的方式返回一個指針時,幾乎可以肯定該指針指向一個動態創建的對象,因此指針的接收者有責任確定該對象最終被清除。這是裸指針的一個很大的缺點:它們沒有傳達任何隱含的所有權聲明,並且必須在代碼之外手動提供關於誰負責動態對象的信息。
1
您創建的對象的析構函數使用new
直到您delete
指針纔會被調用。
爲確保您不會忘記刪除指針,請嘗試使用智能指針,例如std::shared_ptr
或std::unique_ptr
。
如果您的編譯器不夠新以包含智能指針,您可以從Boost中找到一些。
1
當你返回對象的引用時,它不再限定在該函數中,因此不會隨函數而死(即指向該對象的指針不會被刪除)。
-1
C++(.net之外)在你告訴它之前不會刪除一個對象。
1
只有在您錯誤地編寫代碼時纔會發生這種情況。例如:
Foo* MyFunction()
{
Foo foo(2);
return &foo;
} // foo is implicitly destroyed as we return
這是壞了。我收到foo
的地址,但它也因爲超出範圍而被破壞。這很好:
Foo* MyFunction()
{
Foo* j=new Foo(2);
return j;
} // j is implicitly destroyed as we return
這很好。雖然j
由於超出範圍而被銷燬,但我返回的值仍然是我創建的Foo
的地址。我分配的foo
不會被銷燬,因爲它不會超出範圍。
1
有兩種分配對象的方式:堆棧和堆。
1)使用new
關鍵字在堆上創建對象。這些物體直到delete
d才被銷燬。
2)堆棧上存在其他物件 - 否new
,否delete
。這些對象在超出範圍時被銷燬。如果你返回一個指向其中一個對象的指針(通過獲取堆棧分配對象的地址,一旦對象已經超出範圍,指針將會失效)
相關問題
- 1. 爲什麼要調用析構函數,但在將對象作爲參數傳遞時不會調用構造?
- 2. 爲什麼你不能在指針對象上調用函數?
- 3. 爲什麼PHP構造函數不返回可用對象?
- 4. 爲什麼不調用析構函數?
- 5. 爲什麼從對象移動的析構函數被調用?
- 6. 爲什麼對象的構造函數返回Object()而不是構造函數?
- 7. 將返回一個對象調用它的析構函數嗎?
- 8. 析構函數,返回臨時對象
- 9. 爲什麼map :: clear不會調用析構函數?
- 10. 爲什麼在腳本終止時不調用對象析構函數?
- 11. 爲什麼emplace_back調用析構函數?
- 12. Java:爲什麼你需要構造函數來在父類中使用對象?
- 13. 在類構造函數中返回SimpleXML對象 - 爲什麼它不起作用?
- 14. 爲什麼析構函數不按相反順序調用對象數組?
- 15. 在什麼情況下C++析構函數不會被調用?
- 16. 爲什麼由析構函數構造的兩個對象被調用三次
- 17. 函數調用時要使用的JavaScript函數返回對象
- 18. 爲什麼我們不能在const對象上調用函數?
- 19. 對象在JS中返回其構造函數而不是false。爲什麼?
- 20. 函數調用完成後無法解釋析構函數返回對象
- 21. 爲什麼在創建對象時調用構造函數?
- 22. 爲什麼在這個程序中不調用析構函數?
- 23. 爲什麼構造函數返回對象,但不是JavaScript中的基元?
- 24. 什麼時候你會返回一個函數的引用?
- 25. 爲什麼當我傳入不同的對象時,AJAX會將相同的數據返回給回調函數?
- 26. 爲什麼析構函數調用的不止是構造函數?
- 27. 調用析構函數關閉對象
- 28. 當你通過引用返回對象時,你什麼時候需要擔心對象會被銷燬?
- 29. 爲什麼析構函數在返回臨時(右值)時移動構造函數之前調用
- 30. 你認爲parseInt(「08」)會返回什麼?
你可能想提到'static Foo foo(2 ); return &foo;'scenario。 – SigTerm 2012-03-09 23:54:16
爲什麼Foo對象在第二個例子中沒有超出範圍? – 2012-03-09 23:58:52
@badatmath:'Foo *'對象('j')超出了範圍(因爲它具有自動存儲持續時間),但'new Foo(2)'創建的'Foo'具有動態存儲持續時間(並且只有在你明確地銷燬它時纔會被銷燬(使用'delete'))。'new Foo (2)「從來不是真的在一個範圍內(它住在免費商店的以太網中),所以它不能超出範圍 – Mankarse 2012-03-10 00:24:27