2011-12-13 81 views
15

我對C++比較陌生,並且在工作中處理相當大的C++項目。我注意到少數函數將雙指針作爲函數將在堆上實例化的對象的參數。例如:C++爲什麼雙指針出/返回函數參數?

int someFunc(MyClass** retObj) { 
    *retObj = new MyClass(); 

    return 0; 
} 

我只是不確定爲什麼雙指針總是用在這個項目中,而不是一個單一的指針?這大多是一個語義暗示,它是一個out/return參數,還是有更多的技術原因,我沒有看到?

+2

因爲否則你會修改本地副本,而不是保存指針的變量。不要忘記有參考文獻,這是一種更清潔的方式。 – 2011-12-13 19:25:52

+0

我忘記了指針的實際值被複制到了。我以爲它是隱式引用的,但是它來自我的Java背景。 – 2011-12-13 19:41:12

回答

21

使用雙指針模式,以便新分配的MyClass可以傳遞給調用者。例如

MyClass* pValue; 
someFunc(&pValue); 
// pValue now contains the newly allocated MyClass 

單個指針是不夠的,因爲在這裏參數由值用C++傳遞。所以對單個指針的修改只能在someFunc之內看到。

注意:使用C++時,應考慮在此方案中使用引用。

int someFunc(MyClass*& retObj) { 
    retObj = new MyClass(); 
    return 0; 
} 

MyClass* pValue; 
someFunc(pValue); 

這允許您通過引用而不是按值傳遞參數。因此,調用者可以看到結果。

7

簡短的答案是C++中的參數是按值傳遞的,所以你的函數接收到該指針的一個副本。一旦你將它覆蓋在你的函數中,改變就會丟失。

然而,你的代碼段想要從外部看到更改,所以它需要一種方法來覆蓋實際指向該對象的指針,所以它必須獲得指向該類指針的指針副本,因此它可以覆蓋內部指針並從外部可見。

2

使用單個指針是行不通的。考慮:

int someFunc(MyClass* retObj) { 
    retObj = new MyClass(); 
    return 0; 
} 

MyClass* ptr = null; 
someFunc(ptr); 
// ptr is still null and we've got a memory leak 

有些方法可以使這個工作,而不是使用指針指針,其相對優點可以辯論。

3

這兩顆星(雙指針)意味着一個「指針指針」。這是一種繞過限制的方法,您不能從C++中的函數返回兩件事情(在您的情況下,指示成功或失敗的返回代碼以及新分配的對象)。

1

返回X的規範方法是將指針傳遞給X.如果X是「指向MyClass的指針」,則返回它的規範方法是將「指向指向MyClass的指針」傳遞給它。你不能只將一個指向MyClass的指針傳遞給該函數,因爲調用者不知道該指針的值應該是什麼。