2013-01-15 90 views
3

如果我有下面一段代碼順序的std :: unordered_multimap元素

std::unordered_multimap<std::string, std::vector<double>> myMap; 
std::vector<double> v1, v2, v3; 
// init v1, v2, v3.... 
myMap.insert(std::make_pair<std::string, std::vector<double>("vec", v1)); 
myMap.insert(std::make_pair<std::string, std::vector<double>("vec", v2)); 
myMap.insert(std::make_pair<std::string, std::vector<double>("vec", v3)); 

如果我訪問與迭代器的值,他們總是會在這個順序:v1, v2, v3

所以基本上如果我插入相同的鍵的元素,但不同的值,他們總是保留插入的順序?

+2

使用無序容器的最佳方式是根本不考慮順序。完全不依賴訂單。如果您出於某種原因查看元素的順序,則可能是使用了錯誤的容器。不保證它會保留廣告訂單。 – goji

+0

@Troy我可以使用std :: multimap嗎? – djWann

+2

如果你需要在一個容器中使用插入順序,你可能需要類似boost的multi_index。還有其他關於這個問題。 – goji

回答

6

我想這是特定於實現的。在具有相同密鑰的unordered_multimap元素中,如果實現是桶哈希映射,則這些元素將存儲在同一個桶中,在這種情況下,它們可能處於相同的插入順序(可能是您的情況)。

但是在例如使用開放尋址技術實現的unordered_map中,順序可能改變。我不知道是否有STL實現在實現中使用了不同的方法,但是類的合同沒有對同一個鍵的值的順序做任何假設,所以我不認爲你可以把它用於理所當然的。

here摘自:

在內部,在unordered_map的元素是不能以任何特定次序來分類的相對於任一它們的鍵或映射的值

+0

爲了保持插入順序,我可以使用一個簡單的multimap? – djWann

+1

無論使用'unordered_multimap',都沒有值的順序保證,可能在90%以下的實現中工作,但在任何情況下都不會被授予。 – Jack

+0

對不起,我指的是std :: multimap不是std :: unordered_multimap – djWann

4

整點「無序」在名義上是你不能依賴訂單。永遠。

如果您檢測到來自迭代容器的任何訂單,那麼這是實現的巧合或人爲因素。你應該從來沒有指望它。

+2

我認爲你是正確的,但不是無序的部分是指鍵,而不是值? –

+0

@AlexChamberlain,它是指集裝箱所做的保證。在這種情況下,無論是關鍵還是價值都沒有保證。 –

2

除非文檔說明它們總是按照插入順序返回,否則依賴它將會做錯誤的事情。你今天使用的STL實現可能會改變。如果地圖中有很多條目,那麼您使用的實現可能會以不同的方式工作。