00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034 #ifndef _GLIBCXX_PROFILE_UNORDERED_SET
00035 #define _GLIBCXX_PROFILE_UNORDERED_SET 1
00036
00037 #ifndef __GXX_EXPERIMENTAL_CXX0X__
00038 # include <bits/c++0x_warning.h>
00039 #else
00040 # include <unordered_set>
00041
00042 #include <profile/base.h>
00043
00044 #define _GLIBCXX_BASE unordered_set<_Key, _Hash, _Pred, _Alloc>
00045 #define _GLIBCXX_STD_BASE _GLIBCXX_STD_PR::_GLIBCXX_BASE
00046
00047 namespace std
00048 {
00049 namespace __profile
00050 {
00051
00052 template<typename _Key,
00053 typename _Hash = std::hash<_Key>,
00054 typename _Pred = std::equal_to<_Key>,
00055 typename _Alloc = std::allocator<_Key> >
00056 class unordered_set
00057 : public _GLIBCXX_STD_BASE
00058 {
00059 typedef typename _GLIBCXX_STD_BASE _Base;
00060
00061 public:
00062 typedef typename _Base::size_type size_type;
00063 typedef typename _Base::hasher hasher;
00064 typedef typename _Base::key_equal key_equal;
00065 typedef typename _Base::allocator_type allocator_type;
00066 typedef typename _Base::key_type key_type;
00067 typedef typename _Base::value_type value_type;
00068 typedef typename _Base::difference_type difference_type;
00069 typedef typename _Base::reference reference;
00070 typedef typename _Base::const_reference const_reference;
00071
00072 typedef typename _Base::iterator iterator;
00073 typedef typename _Base::const_iterator const_iterator;
00074
00075 explicit
00076 unordered_set(size_type __n = 10,
00077 const hasher& __hf = hasher(),
00078 const key_equal& __eql = key_equal(),
00079 const allocator_type& __a = allocator_type())
00080 : _Base(__n, __hf, __eql, __a)
00081 {
00082 __profcxx_hashtable_construct(this, _Base::bucket_count());
00083 __profcxx_hashtable_construct2(this);
00084 }
00085
00086 template<typename _InputIterator>
00087 unordered_set(_InputIterator __f, _InputIterator __l,
00088 size_type __n = 10,
00089 const hasher& __hf = hasher(),
00090 const key_equal& __eql = key_equal(),
00091 const allocator_type& __a = allocator_type())
00092 : _Base(__f, __l, __n, __hf, __eql, __a)
00093 {
00094 __profcxx_hashtable_construct(this, _Base::bucket_count());
00095 __profcxx_hashtable_construct2(this);
00096 }
00097
00098 unordered_set(const _Base& __x)
00099 : _Base(__x)
00100 {
00101 __profcxx_hashtable_construct(this, _Base::bucket_count());
00102 __profcxx_hashtable_construct2(this);
00103 }
00104
00105 unordered_set(unordered_set&& __x)
00106 : _Base(std::forward<_Base>(__x))
00107 {
00108 __profcxx_hashtable_construct(this, _Base::bucket_count());
00109 __profcxx_hashtable_construct2(this);
00110 }
00111
00112 unordered_set(initializer_list<value_type> __l,
00113 size_type __n = 10,
00114 const hasher& __hf = hasher(),
00115 const key_equal& __eql = key_equal(),
00116 const allocator_type& __a = allocator_type())
00117 : _Base(__l, __n, __hf, __eql, __a) { }
00118
00119 unordered_set&
00120 operator=(const unordered_set& __x)
00121 {
00122 *static_cast<_Base*>(this) = __x;
00123 return *this;
00124 }
00125
00126 unordered_set&
00127 operator=(unordered_set&& __x)
00128 {
00129
00130
00131 this->clear();
00132 this->swap(__x);
00133 return *this;
00134 }
00135
00136 unordered_set&
00137 operator=(initializer_list<value_type> __l)
00138 {
00139 this->clear();
00140 this->insert(__l);
00141 return *this;
00142 }
00143
00144 ~unordered_set()
00145 {
00146 __profcxx_hashtable_destruct(this, _Base::bucket_count(),
00147 _Base::size());
00148 _M_profile_destruct();
00149 }
00150
00151 void
00152 swap(unordered_set& __x)
00153 {
00154 _Base::swap(__x);
00155 }
00156
00157 void
00158 clear()
00159 {
00160 __profcxx_hashtable_destruct(this, _Base::bucket_count(),
00161 _Base::size());
00162 _M_profile_destruct();
00163 _Base::clear();
00164 }
00165
00166 void
00167 insert(std::initializer_list<value_type> __l)
00168 {
00169 size_type __old_size = _Base::bucket_count();
00170 _Base::insert(__l);
00171 _M_profile_resize(__old_size, _Base::bucket_count());
00172 }
00173
00174 std::pair<iterator, bool>
00175 insert(const value_type& __obj)
00176 {
00177 size_type __old_size = _Base::bucket_count();
00178 std::pair<iterator, bool> __res = _Base::insert(__obj);
00179 _M_profile_resize(__old_size, _Base::bucket_count());
00180 return __res;
00181 }
00182
00183 iterator
00184 insert(const_iterator __iter, const value_type& __v)
00185 {
00186 size_type __old_size = _Base::bucket_count();
00187 iterator __res = _Base::insert(__iter, __v);
00188 _M_profile_resize(__old_size, _Base::bucket_count());
00189 return __res;
00190 }
00191
00192 template<typename _InputIter>
00193 void
00194 insert(_InputIter __first, _InputIter __last)
00195 {
00196 size_type __old_size = _Base::bucket_count();
00197 _Base::insert(__first, __last);
00198 _M_profile_resize(__old_size, _Base::bucket_count());
00199 }
00200
00201 void
00202 insert(const value_type* __first, const value_type* __last)
00203 {
00204 size_type __old_size = _Base::bucket_count();
00205 _Base::insert(__first, __last);
00206 _M_profile_resize(__old_size, _Base::bucket_count());
00207 }
00208
00209 void rehash(size_type __n)
00210 {
00211 size_type __old_size = _Base::bucket_count();
00212 _Base::rehash(__n);
00213 _M_profile_resize(__old_size, _Base::bucket_count());
00214 }
00215
00216 private:
00217 _Base&
00218 _M_base() { return *this; }
00219
00220 const _Base&
00221 _M_base() const { return *this; }
00222
00223 void
00224 _M_profile_resize(size_type __old_size, size_type __new_size)
00225 {
00226 if (__old_size != __new_size)
00227 __profcxx_hashtable_resize(this, __old_size, __new_size);
00228 }
00229
00230 void
00231 _M_profile_destruct()
00232 {
00233 size_type __hops = 0, __lc = 0, __chain = 0;
00234 for (iterator __it = _M_base().begin(); __it != _M_base().end();
00235 ++__it)
00236 {
00237 while (__it._M_cur_node->_M_next)
00238 {
00239 ++__chain;
00240 ++__it;
00241 }
00242
00243 if (__chain)
00244 {
00245 ++__chain;
00246 __lc = __lc > __chain ? __lc : __chain;
00247 __hops += __chain * (__chain - 1) / 2;
00248 __chain = 0;
00249 }
00250 }
00251 __profcxx_hashtable_destruct2(this, __lc, _Base::size(), __hops);
00252 }
00253
00254 };
00255
00256 template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
00257 inline void
00258 swap(unordered_set<_Value, _Hash, _Pred, _Alloc>& __x,
00259 unordered_set<_Value, _Hash, _Pred, _Alloc>& __y)
00260 { __x.swap(__y); }
00261
00262 template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
00263 inline bool
00264 operator==(const unordered_set<_Value, _Hash, _Pred, _Alloc>& __x,
00265 const unordered_set<_Value, _Hash, _Pred, _Alloc>& __y)
00266 { return __x._M_equal(__y); }
00267
00268 template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
00269 inline bool
00270 operator!=(const unordered_set<_Value, _Hash, _Pred, _Alloc>& __x,
00271 const unordered_set<_Value, _Hash, _Pred, _Alloc>& __y)
00272 { return !(__x == __y); }
00273
00274 #undef _GLIBCXX_BASE
00275 #undef _GLIBCXX_STD_BASE
00276 #define _GLIBCXX_STD_BASE _GLIBCXX_STD_PR::_GLIBCXX_BASE
00277 #define _GLIBCXX_BASE unordered_multiset<_Value, _Hash, _Pred, _Alloc>
00278
00279
00280 template<typename _Value,
00281 typename _Hash = std::hash<_Value>,
00282 typename _Pred = std::equal_to<_Value>,
00283 typename _Alloc = std::allocator<_Value> >
00284 class unordered_multiset
00285 : public _GLIBCXX_STD_BASE
00286 {
00287 typedef typename _GLIBCXX_STD_BASE _Base;
00288
00289 public:
00290 typedef typename _Base::size_type size_type;
00291 typedef typename _Base::hasher hasher;
00292 typedef typename _Base::key_equal key_equal;
00293 typedef typename _Base::allocator_type allocator_type;
00294 typedef typename _Base::key_type key_type;
00295 typedef typename _Base::value_type value_type;
00296 typedef typename _Base::difference_type difference_type;
00297 typedef typename _Base::reference reference;
00298 typedef typename _Base::const_reference const_reference;
00299
00300 typedef typename _Base::iterator iterator;
00301 typedef typename _Base::const_iterator const_iterator;
00302
00303 explicit
00304 unordered_multiset(size_type __n = 10,
00305 const hasher& __hf = hasher(),
00306 const key_equal& __eql = key_equal(),
00307 const allocator_type& __a = allocator_type())
00308 : _Base(__n, __hf, __eql, __a)
00309 {
00310 __profcxx_hashtable_construct(this, _Base::bucket_count());
00311 }
00312
00313 template<typename _InputIterator>
00314 unordered_multiset(_InputIterator __f, _InputIterator __l,
00315 size_type __n = 10,
00316 const hasher& __hf = hasher(),
00317 const key_equal& __eql = key_equal(),
00318 const allocator_type& __a = allocator_type())
00319 : _Base(__f, __l, __n, __hf, __eql, __a)
00320 {
00321 __profcxx_hashtable_construct(this, _Base::bucket_count());
00322 }
00323
00324 unordered_multiset(const _Base& __x)
00325 : _Base(__x)
00326 {
00327 __profcxx_hashtable_construct(this, _Base::bucket_count());
00328 }
00329
00330 unordered_multiset(unordered_multiset&& __x)
00331 : _Base(std::forward<_Base>(__x))
00332 {
00333 __profcxx_hashtable_construct(this, _Base::bucket_count());
00334 }
00335
00336 unordered_multiset(initializer_list<value_type> __l,
00337 size_type __n = 10,
00338 const hasher& __hf = hasher(),
00339 const key_equal& __eql = key_equal(),
00340 const allocator_type& __a = allocator_type())
00341 : _Base(__l, __n, __hf, __eql, __a) { }
00342
00343 unordered_multiset&
00344 operator=(const unordered_multiset& __x)
00345 {
00346 *static_cast<_Base*>(this) = __x;
00347 return *this;
00348 }
00349
00350 unordered_multiset&
00351 operator=(unordered_multiset&& __x)
00352 {
00353
00354
00355 this->clear();
00356 this->swap(__x);
00357 return *this;
00358 }
00359
00360 unordered_multiset&
00361 operator=(initializer_list<value_type> __l)
00362 {
00363 this->clear();
00364 this->insert(__l);
00365 return *this;
00366 }
00367
00368 ~unordered_multiset()
00369 {
00370 __profcxx_hashtable_destruct(this, _Base::bucket_count(),
00371 _Base::size());
00372 _M_profile_destruct();
00373 }
00374
00375 void
00376 swap(unordered_multiset& __x)
00377 {
00378 _Base::swap(__x);
00379 }
00380
00381 void
00382 clear()
00383 {
00384 __profcxx_hashtable_destruct(this, _Base::bucket_count(),
00385 _Base::size());
00386 _M_profile_destruct();
00387 _Base::clear();
00388 }
00389
00390 void
00391 insert(std::initializer_list<value_type> __l)
00392 {
00393 size_type __old_size = _Base::bucket_count();
00394 _Base::insert(__l);
00395 _M_profile_resize(__old_size, _Base::bucket_count());
00396 }
00397
00398 iterator
00399 insert(const value_type& __obj)
00400 {
00401 size_type __old_size = _Base::bucket_count();
00402 iterator __res = _Base::insert(__obj);
00403 _M_profile_resize(__old_size, _Base::bucket_count());
00404 return __res;
00405 }
00406
00407 iterator
00408 insert(const_iterator __iter, const value_type& __v)
00409 {
00410 size_type __old_size = _Base::bucket_count();
00411 iterator __res = _Base::insert(__iter, __v);
00412 _M_profile_resize(__old_size, _Base::bucket_count());
00413 return __res;
00414 }
00415
00416 template<typename _InputIter>
00417 void
00418 insert(_InputIter __first, _InputIter __last)
00419 {
00420 size_type __old_size = _Base::bucket_count();
00421 _Base::insert(__first, __last);
00422 _M_profile_resize(__old_size, _Base::bucket_count());
00423 }
00424
00425 void
00426 insert(const value_type* __first, const value_type* __last)
00427 {
00428 size_type __old_size = _Base::bucket_count();
00429 _Base::insert(__first, __last);
00430 _M_profile_resize(__old_size, _Base::bucket_count());
00431 }
00432
00433 void rehash(size_type __n)
00434 {
00435 size_type __old_size = _Base::bucket_count();
00436 _Base::rehash(__n);
00437 _M_profile_resize(__old_size, _Base::bucket_count());
00438 }
00439
00440 private:
00441 _Base&
00442 _M_base() { return *this; }
00443
00444 const _Base&
00445 _M_base() const { return *this; }
00446
00447 void
00448 _M_profile_resize(size_type __old_size, size_type __new_size)
00449 {
00450 if (__old_size != __new_size)
00451 __profcxx_hashtable_resize(this, __old_size, __new_size);
00452 }
00453
00454 void
00455 _M_profile_destruct()
00456 {
00457 size_type __hops = 0, __lc = 0, __chain = 0;
00458 for (iterator __it = _M_base().begin(); __it != _M_base().end();
00459 ++__it)
00460 {
00461 while (__it._M_cur_node->_M_next)
00462 {
00463 ++__chain;
00464 ++__it;
00465 }
00466
00467 if (__chain)
00468 {
00469 ++__chain;
00470 __lc = __lc > __chain ? __lc : __chain;
00471 __hops += __chain * (__chain - 1) / 2;
00472 __chain = 0;
00473 }
00474 }
00475 __profcxx_hashtable_destruct2(this, __lc, _Base::size(), __hops);
00476 }
00477
00478 };
00479
00480 template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
00481 inline void
00482 swap(unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __x,
00483 unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __y)
00484 { __x.swap(__y); }
00485
00486 template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
00487 inline bool
00488 operator==(const unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __x,
00489 const unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __y)
00490 { return __x._M_equal(__y); }
00491
00492 template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
00493 inline bool
00494 operator!=(const unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __x,
00495 const unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __y)
00496 { return !(__x == __y); }
00497
00498 }
00499 }
00500
00501 #undef _GLIBCXX_BASE
00502 #undef _GLIBCXX_STD_BASE
00503
00504 #endif // __GXX_EXPERIMENTAL_CXX0X__
00505
00506 #endif