2012-11-18 55 views
5

以下的元素是壞:常量,正確性STD集裝箱

vector<const int> vec; 

的問題是,模板類型必須分配。下面的代碼編譯[編輯:在Visual Studio 2010],這表明上述問題:

vector<const int> vec; 
vec.push_back(6); 
vec[0] += 4; 

使用更復雜的類型,這可能是一個嚴重的問題。

我的第一個問題是,是否有這種行爲的原因。在我看來,可能有可能使const容器不允許使用上述容器和非const容器。

其次,有沒有辦法讓容器以這種方式工作?

第三,這裏實際發生了什麼(用戶類型)?我意識到這是未定義的行爲,但STL甚至如何編譯它呢?

+2

您以未定義的行爲使用標準libray。這意味着有*沒有要求*應該發生什麼。有些操作可能看起來有效,其他操作可能不會。並且在不同的實現之間沒有一致性。 –

+1

這不能在g ++ 4.6.3上編譯。 –

+1

你的代碼不能用C++標準編譯。 –

回答

3

原因std::vector<T const>是不允許的,因爲在插入不同於開頭的位置時,矢量中的對象可能需要重新洗牌。現在,成員std::vector<T>::push_back(T const& v)在概念上等同於(離開分配器模板參數了,因爲它是不相關的討論)

template <typename T> 
void std::vector<T>::push_back(T const& v) { 
    this->insert(this->end(), v); 
} 

這似乎是它是如何在一些實現來實現。現在,這個操作通常需要一些對象可能需要移動,因此參數需要是可分配的。似乎使用MSVC++的標準庫不會委託操作,但會執行所有必要的處理,即在空間不足時適當調整數組大小並移動對象,其格式爲push_back()。目前尚不清楚T型號的要求能夠使用push_back()

在原理上,一個容器支撐既T const和在中間的一個insert()操作將是可能的,雖然:概不要求內部存儲爲T而非typename std::remove_const<T>::type,同時暴露在所述接口中T&。有必要注意const -version ofoperations like operator[](),因爲當T是某種類型時,只使用T const&作爲返回類型S const會導致S const const類型。在C++ 2003中,這將是一個錯誤,在C++ 2011中,我認爲const剛剛崩潰。爲了安全起見,您可以使用typename std::add_const<T>::type&