我偶然發現了這樣的代碼:
void foo(T* bar)/span>。//注意。取得'bar'的所有權。
foo(new T()) 。
現在我想知道是否有必要將其重構為:
void foo(T* bar)。//注意。取得'bar'的所有權。
auto tempT = std::make_unique< T>()。
foo(tempT.release() )。
- 它是否更安全?
- 它當然為所有權的轉移增加了一點明確性,盡管從引數串列中呼叫'new'本身就已經很清楚了。
注意,很遺憾,我不能改變'foo'的簽名。
uj5u.com熱心網友回復:
這是不是更安全的例外?
不是。然而,考慮一個稍微復雜的例子:
auto tempT = std::make_unique< T> ();
some_operation()。
foo(tempT.release()) 。
在這種情況下,如果不使用unique_ptr,就會有一個潛在的例外安全問題。
這就是說,更安全的做法是:
void foo(std: :unique_ptr<T>bar); //不需要注意,采取所有權。
//因為這是由型別暗示的。
注意,不幸的是我不能改變'foo'的簽名。
然后寫一個你能控制的封裝函式。
uj5u.com熱心網友回復:
不,這不是更安全的例外。
但是考慮到如果函式改變為接受更多的引數:
void foo(T* bar, T* more_bar=get_more_bar())。//注意。占用了兩者的所有權。
foo(new T()) 。
現在,如果get_more_bar()在new T()之后被評估,并拋出。
uj5u.com熱心網友回復:
你可以考慮為foo撰寫一個封裝器:
void wrap_foo(std::unique_ptr< T> arg){
foo(arg.get()。
arg.release()。
如果foo拋出一個例外而沒有釋放記憶體,這將釋放它。 然而,如果foo已經是例外安全的,并且在拋出例外之前釋放了記憶體,這將會釋放兩次記憶體。 不幸的是,我們沒有好的方法來撰寫一個安全的包裝器來檢測記憶體是否被正確釋放。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qiye/320006.html
標籤:
