2010-03-24 43 views
19

我想寫一個使用STL分配器的容器類。我現在做的是有一個私有成員如何在我自己的容器類中使用std :: allocator

std::allocator<T> alloc_; 

(這將在稍後進行模板化,使用戶可以選擇不同的分配),然後調用

T* ptr = alloc_.allocate(1,0); 

獲得一個指向新分配'T'對象(並使用alloc_.construct來調用構造函數;請參閱下面的答案)。這適用於GNU C++庫。

但是,使用Solaris上的STLPort時,這不能做正確的事情,並導致各種奇怪的內存損壞錯誤。如果我反而做

std::allocator_interface<std::allocator<T> > alloc_; 

那麼它是所有的工作,因爲它應該。

什麼是使用stl :: allocator的正確方法? STLPort/Solaris版本無法用g ++編譯,但是g ++是正確的?

+7

標準庫中沒有什麼叫'allocator_interface'。 – AraK

回答

8

您可能想要做的事情是您自己定製的allocator,您可以使用它來查看標準容器如何與分配器交互。 Stephan T. Lavavej發佈了一個不錯的簡單的mallocator。拖放到使用各種STL容器測試程序,你可以很容易地看到分配器是如何使用的標準集裝箱:

並不是所有的在mallocator接口功能(如因爲construct()destroy())都裝有跟蹤輸出,因此您可能希望在其中放置跟蹤語句,以便更輕鬆地瞭解標準容器如何使用這些功能而無需使用調試器。

這應該給你一個關於你的容器如何使用自定義allocator的好主意。

+0

不幸的是,它不會跟蹤「構造」,這是他未能使用的功能: -/ –

+0

這是真的(我在我的答案中提到了這個缺點),並且我打算讓我的答案多多少少成爲一個側欄直接指出問題的答案。 Lavavej發佈了'mallocator'作爲自定義分配器的簡單示例。我提出它也可以作爲容易理解容器如何使用分配器的方法,但可能需要做一些小的修改以改進跟蹤。 –

16

您需要同時分配和構建分配器。類似這樣的:

T* ptr = alloc_.allocate(1,0); 
alloc_.construct(ptr, value); 

如果你不從一個正確構造的對象開始,許多事情都徹頭徹尾破碎了。想象一下std::string被分配,但沒有構建。當您嘗試分配給它時,它將首先嚐試通過釋放一些數據來清除其舊內容,這些數據當然是來自堆和崩潰的垃圾值。

+0

是的,我知道,我確實這樣做了,儘管我使用的是placement new而不是std :: allocator :: construct(這可能不值得推薦,所以我現在改變了它)。 但是,事實證明STLPort 4.x不知道std :: allocator ::構造要麼...... –

+0

如果STLPort沒有'std :: allocator :: construct'那麼它被破壞,不要打擾使用它。我可以肯定地告訴你5.1.5(我安裝的版本確實有它並且工作正常)。 –

+1

我期望能夠滿足我的好奇心,STLPort 4.x **確實擁有符合標準的'std :: allocator'。在4.6中,'construct'函數可以在'stlport/stl/_alloc.h'的第365行找到。如果它不起作用,則說明安裝不正確。 –

相關問題