00001
00002
00003
00004
00005
00006
00007
00008
00009
00012 #ifndef MULTIMAP_HPP
00013 #define MULTIMAP_HPP
00014
00015 #include <map>
00016 #include <list>
00017
00018 template<typename Tkey, typename Tvalue, typename Tcompare>
00019 class MultiMap;
00020
00029 template<class Tmap_iter, class Tlist_iter, class Tkey, class Tvalue, class Tcompare>
00030 class MultiMapIterator {
00031 protected:
00032 friend class MultiMap<Tkey, Tvalue, Tcompare>;
00033 typedef MultiMapIterator<Tmap_iter, Tlist_iter, Tkey, Tvalue, Tcompare> Self;
00034
00035 Tlist_iter list_iter;
00036 Tmap_iter map_iter;
00037
00047 bool list_valid;
00048
00049 public:
00053 MultiMapIterator() : list_valid(false) {}
00054
00061 template<class Tnon_const>
00062 MultiMapIterator(Tnon_const mi) : map_iter(mi), list_valid(false) {}
00063
00071 MultiMapIterator(Tmap_iter mi, Tlist_iter li) : list_iter(li), map_iter(mi)
00072 {
00073 this->list_valid = (this->list_iter != this->map_iter->second.begin());
00074 }
00075
00082 template<class Tnon_const>
00083 Self &operator=(Tnon_const mi)
00084 {
00085 this->map_iter = mi;
00086 this->list_valid = false;
00087 return *this;
00088 }
00089
00095 Tvalue &operator*() const
00096 {
00097 assert(!this->map_iter->second.empty());
00098 return this->list_valid ?
00099 this->list_iter.operator*() :
00100 this->map_iter->second.begin().operator*();
00101 }
00102
00107 Tvalue *operator->() const
00108 {
00109 assert(!this->map_iter->second.empty());
00110 return this->list_valid ?
00111 this->list_iter.operator->() :
00112 this->map_iter->second.begin().operator->();
00113 }
00114
00115 inline const Tmap_iter &GetMapIter() const { return this->map_iter; }
00116 inline const Tlist_iter &GetListIter() const { return this->list_iter; }
00117 inline bool ListValid() const { return this->list_valid; }
00118
00119 const Tkey &GetKey() const { return this->map_iter->first; }
00120
00127 Self &operator++()
00128 {
00129 assert(!this->map_iter->second.empty());
00130 if (this->list_valid) {
00131 if (++this->list_iter == this->map_iter->second.end()) {
00132 ++this->map_iter;
00133 this->list_valid = false;
00134 }
00135 } else {
00136 this->list_iter = ++(this->map_iter->second.begin());
00137 if (this->list_iter == this->map_iter->second.end()) {
00138 ++this->map_iter;
00139 } else {
00140 this->list_valid = true;
00141 }
00142 }
00143 return *this;
00144 }
00145
00152 Self operator++(int)
00153 {
00154 Self tmp = *this;
00155 this->operator++();
00156 return tmp;
00157 }
00158
00164 Self &operator--()
00165 {
00166 assert(!this->map_iter->second.empty());
00167 if (!this->list_valid) {
00168 --this->map_iter;
00169 this->list_iter = this->map_iter->second.end();
00170 assert(!this->map_iter->second.empty());
00171 }
00172
00173 this->list_valid = (--this->list_iter != this->map_iter->second.begin());
00174 return *this;
00175 }
00176
00183 Self operator--(int)
00184 {
00185 Self tmp = *this;
00186 this->operator--();
00187 return tmp;
00188 }
00189 };
00190
00191
00192
00204 template<class Tmap_iter1, class Tlist_iter1, class Tmap_iter2, class Tlist_iter2, class Tkey, class Tvalue1, class Tvalue2, class Tcompare>
00205 bool operator==(const MultiMapIterator<Tmap_iter1, Tlist_iter1, Tkey, Tvalue1, Tcompare> &iter1, const MultiMapIterator<Tmap_iter2, Tlist_iter2, Tkey, Tvalue2, Tcompare> &iter2)
00206 {
00207 if (iter1.GetMapIter() != iter2.GetMapIter()) return false;
00208 if (!iter1.ListValid()) return !iter2.ListValid();
00209 return iter2.ListValid() ?
00210 iter1.GetListIter() == iter2.GetListIter() : false;
00211 }
00212
00221 template<class Tmap_iter1, class Tlist_iter1, class Tmap_iter2, class Tlist_iter2, class Tkey, class Tvalue1, class Tvalue2, class Tcompare>
00222 bool operator!=(const MultiMapIterator<Tmap_iter1, Tlist_iter1, Tkey, Tvalue1, Tcompare> &iter1, const MultiMapIterator<Tmap_iter2, Tlist_iter2, Tkey, Tvalue2, Tcompare> &iter2)
00223 {
00224 return !(iter1 == iter2);
00225 }
00226
00235 template<class Tmap_iter1, class Tlist_iter1, class Tmap_iter2, class Tkey, class Tvalue, class Tcompare >
00236 bool operator==(const MultiMapIterator<Tmap_iter1, Tlist_iter1, Tkey, Tvalue, Tcompare> &iter1, const Tmap_iter2 &iter2)
00237 {
00238 return !iter1.ListValid() && iter1.GetMapIter() == iter2;
00239 }
00240
00247 template<class Tmap_iter1, class Tlist_iter1, class Tmap_iter2, class Tkey, class Tvalue, class Tcompare >
00248 bool operator!=(const MultiMapIterator<Tmap_iter1, Tlist_iter1, Tkey, Tvalue, Tcompare> &iter1, const Tmap_iter2 &iter2)
00249 {
00250 return iter1.ListValid() || iter1.GetMapIter() != iter2;
00251 }
00252
00259 template<class Tmap_iter1, class Tlist_iter1, class Tmap_iter2, class Tkey, class Tvalue, class Tcompare >
00260 bool operator==(const Tmap_iter2 &iter2, const MultiMapIterator<Tmap_iter1, Tlist_iter1, Tkey, Tvalue, Tcompare> &iter1)
00261 {
00262 return !iter1.ListValid() && iter1.GetMapIter() == iter2;
00263 }
00264
00271 template<class Tmap_iter1, class Tlist_iter1, class Tmap_iter2, class Tkey, class Tvalue, class Tcompare >
00272 bool operator!=(const Tmap_iter2 &iter2, const MultiMapIterator<Tmap_iter1, Tlist_iter1, Tkey, Tvalue, Tcompare> &iter1)
00273 {
00274 return iter1.ListValid() || iter1.GetMapIter() != iter2;
00275 }
00276
00277
00285 template<typename Tkey, typename Tvalue, typename Tcompare = std::less<Tkey> >
00286 class MultiMap : public std::map<Tkey, std::list<Tvalue>, Tcompare > {
00287 public:
00288 typedef typename std::list<Tvalue> List;
00289 typedef typename List::iterator ListIterator;
00290 typedef typename List::const_iterator ConstListIterator;
00291
00292 typedef typename std::map<Tkey, List, Tcompare > Map;
00293 typedef typename Map::iterator MapIterator;
00294 typedef typename Map::const_iterator ConstMapIterator;
00295
00296 typedef MultiMapIterator<MapIterator, ListIterator, Tkey, Tvalue, Tcompare> iterator;
00297 typedef MultiMapIterator<ConstMapIterator, ConstListIterator, Tkey, const Tvalue, Tcompare> const_iterator;
00298
00304 iterator erase(iterator it)
00305 {
00306 List &list = it.map_iter->second;
00307 assert(!list.empty());
00308 if (it.list_valid) {
00309 it.list_iter = list.erase(it.list_iter);
00310
00311
00312 if (it.list_iter == list.end()) {
00313 ++it.map_iter;
00314 it.list_valid = false;
00315 }
00316 } else {
00317 list.erase(list.begin());
00318 if (list.empty()) this->Map::erase(it.map_iter++);
00319 }
00320 return it;
00321 }
00322
00328 void Insert(const Tkey &key, const Tvalue &val)
00329 {
00330 List &list = (*this)[key];
00331 list.push_back(val);
00332 assert(!list.empty());
00333 }
00334
00339 size_t size() const
00340 {
00341 size_t ret = 0;
00342 for (ConstMapIterator it = this->Map::begin(); it != this->Map::end(); ++it) {
00343 ret += it->second.size();
00344 }
00345 return ret;
00346 }
00347
00352 size_t MapSize() const
00353 {
00354 return this->Map::size();
00355 }
00356
00362 std::pair<iterator, iterator> equal_range(const Tkey &key)
00363 {
00364 MapIterator begin(this->lower_bound(key));
00365 if (begin != this->Map::end() && begin->first == key) {
00366 MapIterator end = begin;
00367 return std::make_pair(begin, ++end);
00368 }
00369 return std::make_pair(begin, begin);
00370 }
00371
00377 std::pair<const_iterator, const_iterator> equal_range(const Tkey &key) const
00378 {
00379 ConstMapIterator begin(this->lower_bound(key));
00380 if (begin != this->Map::end() && begin->first == key) {
00381 ConstMapIterator end = begin;
00382 return std::make_pair(begin, ++end);
00383 }
00384 return std::make_pair(begin, begin);
00385 }
00386 };
00387
00388 #endif