Table of Contents
1 避免 \(set \& multiset\) 在原位改變 Key
set, multiset, map, multimap 都是有序的容器,若是直接在原位改變 key 的值,則頗有可能容器不有序,後續對該容器的算法會失效。 css
2 Consider replacing associative containers with sorted vectors
Associative Container 中的每一個 Node 除了保存真正對象外,還須要維護指向 Parent, Previous, Next 的三個指針,相比 vector 來講,更佔用內存,範文時間爲 O(logn)。 而 vectors,若是配合合適的 Hash Function ,則既省時間又省空間,但不足之處是須要本身始終維持 vector 在有序的狀態。 java
3 Choose carefully between map::operator[] and map-insert
map::operator[] 會返回 Value 的一個引用,而若是對應的 Key 在 Map 中沒有 Value, map 會調用 Default Constructor 來建立一個新的,加到 Map 中,而後再將新的 Value 返回出來,例如,下面的代碼中: c++
1: class Widget 2: { 3: public: 4: Widget(){} 5: Widget(double d):m_value(d){} 6: virtual ~Widget(){} 7: private: 8: double m_value; 9: }; 10: 11: map<int, Widget> m; 12: m[1] = 1.50;
第 12 行一行代碼實際上和下面的代碼是等效的: 算法
13: pair<map<int, Widget>::iterator, bool> result = 14: m.insert(map<int, Widget>::value_type(1, Widget())); 15: result.first->second = 1.50;
實際上,咱們能夠用下面的一行代碼來完成所需操做,避免無謂的默認構造: sql
m.insert(map<int, Widget>::value_type(1, 1.50));
但若是咱們想更新已有的 Key, 則 [ ] 更簡單一些。 bash
書中最後給出了一個例子,用於高效的添加或者更新 map: ide
1: template <typename MapType, 2: typename KeyType, 3: typename ValueType> 4: typename MapType::iterator 5: efficientAddOrUpdate(MapType& map, 6: cons KeyType& k, 7: const ValueType& v) 8: { 9: typename MapType::iterator lb = m.lower_bound(k); 10: if (lb != m.end() && !(m.key_comp()(k, lb->first))) 11: { 12: lb->second = v; 13: return lb; 14: } 15: else 16: { 17: typedef typename MapType::value_type MVT; 18: return m.insert(lb, MVT(k,v)); 19: } 20: }