2011-08-19 46 views
4

我儘量避免指針,而不是做性病避免指針::名單

std::list<std::pair<int,int>* > myList; 
void addElement(int a, int b) { 
    myList.push_back(new std::pair<int,int>(a,b)); 
} 

我想我可以做這樣

std::list<std::pair<int,int> > myList; 
void addElement(int a, int b) { 
    std::pair<int,int> p(a,b); 
    myList.push_back(p); 
} 

東西如果我理解正確的行爲,這應該存儲該副本的副本,並在執行myList.clear()(而不是指針)時自動將其刪除。

這是最好的方法嗎? 我可以期待編譯器優化不必要的對象p

+4

它是否重要,如果它是優化或不(成本將是微不足道的)。 –

+6

您正在將一個項目添加到列表中,這將導致堆分配,並且會在列表的每次迭代中導致大量的緩存未命中 - 並且您擔心複製兩個整數? –

+0

我很擔心在我的代碼中處理指針,並導致內存泄漏。我要求獲得一些更有經驗的實施意見,以確保我沒有做任何特別愚蠢的事情。我感謝所有的評論和回覆。 –

回答

8

「我可以期待編譯器優化掉不必要的對象p嗎?」

也許,也許不是。儘管試試這個:

myList.push_back(std::make_pair(a,b)); 

如果在適用的情況下使用r值,那麼通常有更好的優化機會。

但即使它沒有優化,這是沒有理由訴諸使用指針,特別是對於這樣的小對象(而不是我主張使用大對象指針)。只有在語義上使用指針時才使用指針,這很少見。

5

在C++ 0x中,您可以使用std::list::emplace_back,它使用完美轉發將參數傳遞給對象構造函數,從而在原地創建std::pair。但否則不。它需要創建一個臨時的。

1

期望拷貝被優化出來是不合理的。它可能是,但有些可疑。

主要問題是函數的參數必須在函數被調用前完全評估,所以對於一對int的情況它可能確實有效(它可以內聯,因此編譯器可以看到沒有異常/側面效果),一般來說顯然不合理。

另一方面,考慮到動態內存分配的高成本,副本約束無論如何在這種特殊情況下更便宜!