問題描述
我有一個作為 std::map
實現的符號表.對于值,無法通過默認構造函數合法地構造值類型的實例.但是,如果我不提供默認構造函數,則會出現編譯器錯誤,如果我使構造函數斷言,我的程序可以正常編譯但在 map<K,V>::operator []
如果我嘗試使用它來添加新成員.
I have a symbol table implemented as a std::map
. For the value, there is no way to legitimately construct an instance of the value type via a default constructor. However if I don't provide a default constructor, I get a compiler error and if I make the constructor assert, my program compile just fine but crashes inside of map<K,V>::operator []
if I try to use it to add a new member.
有沒有辦法讓 C++ 在編譯時禁止 map[k]
作為左值(同時允許它作為 r 值)?
Is there a way I can get C++ to disallow map[k]
as an l-value at compile time (while allowing it as an r-value)?
順便說一句:我知道我可以使用 Map.insert(map<K,V>::value_type(k,v))
插入到地圖中.
BTW: I know I can insert into the map using Map.insert(map<K,V>::value_type(k,v))
.
一些人提出了相當于改變值類型的解決方案,以便地圖可以在不調用默認構造函數的情況下構造一個.這與我想要的結果完全相反,因為它將錯誤隱藏到以后.如果我愿意,我可以簡單地從構造函數中刪除斷言.我想要是讓錯誤發生得更快;在編譯時.但是,似乎沒有辦法區分 operator[]
的 r-value 和 l-value 使用,所以看起來我想要的東西無法完成,所以我只需要分配一起使用.
several people have proposed solution that amount to altering the type of the value so that the map can construct one without calling the default constructor. This has exactly the opposite result of what I want because it hides the error until later. If I were willing to have that, I could simply remove the assert from the constructor. What I Want is to make the error happen even sooner; at compile time. However, it seems that there is no way to distinguish between r-value and l-value uses of operator[]
so it seems what I want can't be done so I'll just have to dispense with using it all together.
推薦答案
你不能讓編譯器區分 operator[] 的兩種用法,因為它們是同一個東西.Operator[] 返回一個引用,因此分配版本只是分配給該引用.
You can't make the compiler differentiate between the two uses of operator[], because they are the same thing. Operator[] returns a reference, so the assignment version is just assigning to that reference.
就我個人而言,除了快速和骯臟的演示代碼之外,我從不使用運算符 [] 來表示地圖.使用 insert() 和 find() 代替.請注意,make_pair() 函數使插入更易于使用:
Personally, I never use operator[] for maps for anything but quick and dirty demo code. Use insert() and find() instead. Note that the make_pair() function makes insert easier to use:
m.insert( make_pair( k, v ) );
<小時>
在 C++11 中,你也可以這樣做
In C++11, you can also do
m.emplace( k, v );
m.emplace( piecewise_construct, make_tuple(k), make_tuple(the_constructor_arg_of_v) );
即使沒有提供復制/移動構造函數.
even if the copy/move constructor is not supplied.
這篇關于使用 std::map<K,V>其中 V 沒有可用的默認構造函數的文章就介紹到這了,希望我們推薦的答案對大家有所幫助,也希望大家多多支持html5模板網!