map插入物件小結

2021-05-04 14:50:54 字數 3516 閱讀 3905

難道插入map還有什麼講究嗎?我們且看map在stl中的定義方法:

template , class alloc = alloc>

第乙個引數key是關鍵字型別

第二個引數t是值型別

第三個引數compare是比較函式(仿函式)

第四個引數是記憶體配置物件

map內部儲存機制實際是以紅黑樹為基礎,紅黑樹在插入節點時,必須依照大小比對之後在乙個合適的位置上執行插入動作。所以作為關鍵字,起碼必須有「<」這個比較操作符。我們知道,int,float,enum,size_t等等簡單關鍵字,都有內建的比較函式,與map搭配無論是插入還是查詢,都沒什麼問題。但是作為複雜資料型別,如果沒有明確定義「

<」比較操作符,就不能與map直接搭配使用,除非我們自己定義第三個引數。

在選擇map的關鍵字時,注意以下兩點,同時這兩點也是改錯的方法:

a) 關鍵字明確定義「

<」比較操作符

b) 沒有「

<」比較操作符,自定義仿函式替代第三個引數compare,該仿函式實現「()」操作符,提供比較功能。插入時各節點順序以該仿函式為綱。

下面我們先寫乙個有錯誤的函式,在分析錯誤原因之後,逐步進行修正。

#include

int main()

std::map, int> res;

res.insert(std::make_pair(12,33), 33);

這個程式一定失敗,如果非要如此使用,上述a方法顯然不適合,std::pair是已定義好的結構體不可修改。只能使用b方法了,定義乙個比較類改造如下:

#include

struct comp

typedef std::pairvalue_type;

bool operator () (const value_type & ls, const value_type &rs)

return ls.first < rs.first || (ls.first == rs.first && ls.second < rs.second);

int main()

std::map, int, comp> res;

res.insert(std::make_pair(std::make_pair(12,33), 33));

res.insert(std::make_pair(std::make_pair(121,331), 331));

res.insert(std::make_pair(std::make_pair(122,332), 332));

std::map, int, comp>::iterator it = res.find(std::make_pair(121,331));

if (it == res.end())

printf("null"n");

else

printf("%d %d %d "n", it->first.first, it->first.second, it->second);

return 0;

#include

struct st

int a, b;

st():a(0), b(0){}

st(int x, int y):a(x), b(y){}

int main()

std::mapres;

res.insert(std::make_pair(st(1,2), 12));

res.insert(std::make_pair(st(30,4), 34));

res.insert(std::make_pair(st(5,6), 56));

std::map::iterator it = res.find(st(30,4));

if (it == res.end())

printf("null"n");

else

printf("first:%d second:%d %d"n", it->first.a, it->first.b, it->second);

return 0;

編譯這個程式也是錯誤的,錯誤意思大概也是沒有定義「

<」比較函式。因為struct st是我們自己定義的結構體,所以修改這個程式可以使用上面a、b兩種方法。我們先談第一種,第一次修改時我也搞錯了,我是這樣定義比較函式的。

struct st

int a, b;

st():a(0), b(0){}

st(int x, int y):a(x), b(y){}

bool operator < (const struct st &rs)

/usr/include/c++/3.2.3/bits/stl_function.h:197: passing `const st' as `this' argument of `bool st::operator<(const st&)' discards qualifiers

為什麼會出現這個

問題呢?我們深入stl的源**看下。既然說是/usr/include/c++/3.2.3/bits/stl_function.h的197行出了問題,且看這行是什麼。

193 /// one of the @link s20_3_3_comparisons comparison functors@endlink.

194 template

195 struct less : public binary_function<_tp,_tp,bool>

196 

198 };

struct st中的「

<」在編譯後真正是什麼樣子呢?大概是bool operator < (struct st &ls, const struct st &rs)。在less呼叫這個比較符時,它都是以const方式傳入,不可能再以非const方式呼叫,故出錯。修正如下:

struct st

int a, b;

st():a(0), b(0){}

st(int x, int y):a(x), b(y){}

friend bool operator < (const struct st &ls, const struct st &rs);

inline bool operator < (const struct st &ls, const struct st &rs)

以友聯函式代替函式內部定義的比較操作符,stl內部也多是以這種方式定義的。如果我非要以內部定義的方式呢?可以使用b方法,我們自定義乙個比較仿函式,替代預設的less。

在map容器中插入資料有很多函式可用,這裡只討論最普通的insert操作,在stl中它是這樣定義的。

pairinsert(const value_type& x);

map容器不允許鍵值重複,在執行插入操作後,可以憑藉該返回值獲取操作結果。返回值是乙個迭代器和布林值的鍵值對,迭代器指向map中具有該值的元素,布林值表示是否插入成功。如果布林值為true,表示插入成功,則迭代器為新插入值在map中的位置;布林值為false,表示插入失敗(已經存在該值),迭代器為原有值在map中的位置。

map插入物件小結

難道插入map還有什麼講究嗎?我們且看map在stl中的定義方法 template class alloc alloc 第乙個引數key是關鍵字型別 第二個引數t是值型別 第三個引數compare是比較函式 仿函式 第四個引數是記憶體配置物件 map內部儲存機制實際是以紅黑樹為基礎,紅黑樹在插入節點...

map中插入資料

在構造map容器後,我們就可以往裡面插入資料了。這裡講四種插入資料的方法 第一種 用insert函式插入pair資料 在vc下 入這條語句,遮蔽4786警告 pragma warning disable 4786 mapmapstudent mapstudent.insert pair 1,stud...

STL map 插入小結

難道插入map還有什麼講究嗎?我們且看map在stl中的定義方法 template class compare less,class alloc alloc 第乙個引數key是關鍵字型別 第二個引數t是值型別 第三個引數compare是比較函式 仿函式 第四個引數是記憶體配置物件 map內部儲存機制...