unordered_set 35 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165
  1. // Debugging unordered_set/unordered_multiset implementation -*- C++ -*-
  2. // Copyright (C) 2003-2018 Free Software Foundation, Inc.
  3. //
  4. // This file is part of the GNU ISO C++ Library. This library is free
  5. // software; you can redistribute it and/or modify it under the
  6. // terms of the GNU General Public License as published by the
  7. // Free Software Foundation; either version 3, or (at your option)
  8. // any later version.
  9. // This library is distributed in the hope that it will be useful,
  10. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. // GNU General Public License for more details.
  13. // Under Section 7 of GPL version 3, you are granted additional
  14. // permissions described in the GCC Runtime Library Exception, version
  15. // 3.1, as published by the Free Software Foundation.
  16. // You should have received a copy of the GNU General Public License and
  17. // a copy of the GCC Runtime Library Exception along with this program;
  18. // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
  19. // <http://www.gnu.org/licenses/>.
  20. /** @file debug/unordered_set
  21. * This file is a GNU debug extension to the Standard C++ Library.
  22. */
  23. #ifndef _GLIBCXX_DEBUG_UNORDERED_SET
  24. #define _GLIBCXX_DEBUG_UNORDERED_SET 1
  25. #pragma GCC system_header
  26. #if __cplusplus < 201103L
  27. # include <bits/c++0x_warning.h>
  28. #else
  29. # include <unordered_set>
  30. #include <debug/safe_unordered_container.h>
  31. #include <debug/safe_container.h>
  32. #include <debug/safe_iterator.h>
  33. #include <debug/safe_local_iterator.h>
  34. namespace std _GLIBCXX_VISIBILITY(default)
  35. {
  36. namespace __debug
  37. {
  38. /// Class std::unordered_set with safety/checking/debug instrumentation.
  39. template<typename _Value,
  40. typename _Hash = std::hash<_Value>,
  41. typename _Pred = std::equal_to<_Value>,
  42. typename _Alloc = std::allocator<_Value> >
  43. class unordered_set
  44. : public __gnu_debug::_Safe_container<
  45. unordered_set<_Value, _Hash, _Pred, _Alloc>, _Alloc,
  46. __gnu_debug::_Safe_unordered_container>,
  47. public _GLIBCXX_STD_C::unordered_set<_Value, _Hash, _Pred, _Alloc>
  48. {
  49. typedef _GLIBCXX_STD_C::unordered_set<
  50. _Value, _Hash, _Pred, _Alloc> _Base;
  51. typedef __gnu_debug::_Safe_container<
  52. unordered_set, _Alloc, __gnu_debug::_Safe_unordered_container> _Safe;
  53. typedef typename _Base::const_iterator _Base_const_iterator;
  54. typedef typename _Base::iterator _Base_iterator;
  55. typedef typename _Base::const_local_iterator _Base_const_local_iterator;
  56. typedef typename _Base::local_iterator _Base_local_iterator;
  57. public:
  58. typedef typename _Base::size_type size_type;
  59. typedef typename _Base::hasher hasher;
  60. typedef typename _Base::key_equal key_equal;
  61. typedef typename _Base::allocator_type allocator_type;
  62. typedef typename _Base::key_type key_type;
  63. typedef typename _Base::value_type value_type;
  64. typedef __gnu_debug::_Safe_iterator<
  65. _Base_iterator, unordered_set> iterator;
  66. typedef __gnu_debug::_Safe_iterator<
  67. _Base_const_iterator, unordered_set> const_iterator;
  68. typedef __gnu_debug::_Safe_local_iterator<
  69. _Base_local_iterator, unordered_set> local_iterator;
  70. typedef __gnu_debug::_Safe_local_iterator<
  71. _Base_const_local_iterator, unordered_set> const_local_iterator;
  72. unordered_set() = default;
  73. explicit
  74. unordered_set(size_type __n,
  75. const hasher& __hf = hasher(),
  76. const key_equal& __eql = key_equal(),
  77. const allocator_type& __a = allocator_type())
  78. : _Base(__n, __hf, __eql, __a) { }
  79. template<typename _InputIterator>
  80. unordered_set(_InputIterator __first, _InputIterator __last,
  81. size_type __n = 0,
  82. const hasher& __hf = hasher(),
  83. const key_equal& __eql = key_equal(),
  84. const allocator_type& __a = allocator_type())
  85. : _Base(__gnu_debug::__base(__gnu_debug::__check_valid_range(__first,
  86. __last)),
  87. __gnu_debug::__base(__last), __n,
  88. __hf, __eql, __a) { }
  89. unordered_set(const unordered_set&) = default;
  90. unordered_set(const _Base& __x)
  91. : _Base(__x) { }
  92. unordered_set(unordered_set&&) = default;
  93. explicit
  94. unordered_set(const allocator_type& __a)
  95. : _Base(__a) { }
  96. unordered_set(const unordered_set& __uset,
  97. const allocator_type& __a)
  98. : _Base(__uset, __a) { }
  99. unordered_set(unordered_set&& __uset,
  100. const allocator_type& __a)
  101. : _Safe(std::move(__uset._M_safe()), __a),
  102. _Base(std::move(__uset._M_base()), __a) { }
  103. unordered_set(initializer_list<value_type> __l,
  104. size_type __n = 0,
  105. const hasher& __hf = hasher(),
  106. const key_equal& __eql = key_equal(),
  107. const allocator_type& __a = allocator_type())
  108. : _Base(__l, __n, __hf, __eql, __a) { }
  109. unordered_set(size_type __n, const allocator_type& __a)
  110. : unordered_set(__n, hasher(), key_equal(), __a)
  111. { }
  112. unordered_set(size_type __n, const hasher& __hf,
  113. const allocator_type& __a)
  114. : unordered_set(__n, __hf, key_equal(), __a)
  115. { }
  116. template<typename _InputIterator>
  117. unordered_set(_InputIterator __first, _InputIterator __last,
  118. size_type __n,
  119. const allocator_type& __a)
  120. : unordered_set(__first, __last, __n, hasher(), key_equal(), __a)
  121. { }
  122. template<typename _InputIterator>
  123. unordered_set(_InputIterator __first, _InputIterator __last,
  124. size_type __n, const hasher& __hf,
  125. const allocator_type& __a)
  126. : unordered_set(__first, __last, __n, __hf, key_equal(), __a)
  127. { }
  128. unordered_set(initializer_list<value_type> __l,
  129. size_type __n,
  130. const allocator_type& __a)
  131. : unordered_set(__l, __n, hasher(), key_equal(), __a)
  132. { }
  133. unordered_set(initializer_list<value_type> __l,
  134. size_type __n, const hasher& __hf,
  135. const allocator_type& __a)
  136. : unordered_set(__l, __n, __hf, key_equal(), __a)
  137. { }
  138. ~unordered_set() = default;
  139. unordered_set&
  140. operator=(const unordered_set&) = default;
  141. unordered_set&
  142. operator=(unordered_set&&) = default;
  143. unordered_set&
  144. operator=(initializer_list<value_type> __l)
  145. {
  146. _M_base() = __l;
  147. this->_M_invalidate_all();
  148. return *this;
  149. }
  150. void
  151. swap(unordered_set& __x)
  152. noexcept( noexcept(declval<_Base&>().swap(__x)) )
  153. {
  154. _Safe::_M_swap(__x);
  155. _Base::swap(__x);
  156. }
  157. void
  158. clear() noexcept
  159. {
  160. _Base::clear();
  161. this->_M_invalidate_all();
  162. }
  163. iterator
  164. begin() noexcept
  165. { return iterator(_Base::begin(), this); }
  166. const_iterator
  167. begin() const noexcept
  168. { return const_iterator(_Base::begin(), this); }
  169. iterator
  170. end() noexcept
  171. { return iterator(_Base::end(), this); }
  172. const_iterator
  173. end() const noexcept
  174. { return const_iterator(_Base::end(), this); }
  175. const_iterator
  176. cbegin() const noexcept
  177. { return const_iterator(_Base::begin(), this); }
  178. const_iterator
  179. cend() const noexcept
  180. { return const_iterator(_Base::end(), this); }
  181. // local versions
  182. local_iterator
  183. begin(size_type __b)
  184. {
  185. __glibcxx_check_bucket_index(__b);
  186. return local_iterator(_Base::begin(__b), this);
  187. }
  188. local_iterator
  189. end(size_type __b)
  190. {
  191. __glibcxx_check_bucket_index(__b);
  192. return local_iterator(_Base::end(__b), this);
  193. }
  194. const_local_iterator
  195. begin(size_type __b) const
  196. {
  197. __glibcxx_check_bucket_index(__b);
  198. return const_local_iterator(_Base::begin(__b), this);
  199. }
  200. const_local_iterator
  201. end(size_type __b) const
  202. {
  203. __glibcxx_check_bucket_index(__b);
  204. return const_local_iterator(_Base::end(__b), this);
  205. }
  206. const_local_iterator
  207. cbegin(size_type __b) const
  208. {
  209. __glibcxx_check_bucket_index(__b);
  210. return const_local_iterator(_Base::cbegin(__b), this);
  211. }
  212. const_local_iterator
  213. cend(size_type __b) const
  214. {
  215. __glibcxx_check_bucket_index(__b);
  216. return const_local_iterator(_Base::cend(__b), this);
  217. }
  218. size_type
  219. bucket_size(size_type __b) const
  220. {
  221. __glibcxx_check_bucket_index(__b);
  222. return _Base::bucket_size(__b);
  223. }
  224. float
  225. max_load_factor() const noexcept
  226. { return _Base::max_load_factor(); }
  227. void
  228. max_load_factor(float __f)
  229. {
  230. __glibcxx_check_max_load_factor(__f);
  231. _Base::max_load_factor(__f);
  232. }
  233. template<typename... _Args>
  234. std::pair<iterator, bool>
  235. emplace(_Args&&... __args)
  236. {
  237. size_type __bucket_count = this->bucket_count();
  238. std::pair<_Base_iterator, bool> __res
  239. = _Base::emplace(std::forward<_Args>(__args)...);
  240. _M_check_rehashed(__bucket_count);
  241. return std::make_pair(iterator(__res.first, this), __res.second);
  242. }
  243. template<typename... _Args>
  244. iterator
  245. emplace_hint(const_iterator __hint, _Args&&... __args)
  246. {
  247. __glibcxx_check_insert(__hint);
  248. size_type __bucket_count = this->bucket_count();
  249. _Base_iterator __it = _Base::emplace_hint(__hint.base(),
  250. std::forward<_Args>(__args)...);
  251. _M_check_rehashed(__bucket_count);
  252. return iterator(__it, this);
  253. }
  254. std::pair<iterator, bool>
  255. insert(const value_type& __obj)
  256. {
  257. size_type __bucket_count = this->bucket_count();
  258. std::pair<_Base_iterator, bool> __res
  259. = _Base::insert(__obj);
  260. _M_check_rehashed(__bucket_count);
  261. return std::make_pair(iterator(__res.first, this), __res.second);
  262. }
  263. iterator
  264. insert(const_iterator __hint, const value_type& __obj)
  265. {
  266. __glibcxx_check_insert(__hint);
  267. size_type __bucket_count = this->bucket_count();
  268. _Base_iterator __it = _Base::insert(__hint.base(), __obj);
  269. _M_check_rehashed(__bucket_count);
  270. return iterator(__it, this);
  271. }
  272. std::pair<iterator, bool>
  273. insert(value_type&& __obj)
  274. {
  275. size_type __bucket_count = this->bucket_count();
  276. std::pair<_Base_iterator, bool> __res
  277. = _Base::insert(std::move(__obj));
  278. _M_check_rehashed(__bucket_count);
  279. return std::make_pair(iterator(__res.first, this), __res.second);
  280. }
  281. iterator
  282. insert(const_iterator __hint, value_type&& __obj)
  283. {
  284. __glibcxx_check_insert(__hint);
  285. size_type __bucket_count = this->bucket_count();
  286. _Base_iterator __it = _Base::insert(__hint.base(), std::move(__obj));
  287. _M_check_rehashed(__bucket_count);
  288. return iterator(__it, this);
  289. }
  290. void
  291. insert(std::initializer_list<value_type> __l)
  292. {
  293. size_type __bucket_count = this->bucket_count();
  294. _Base::insert(__l);
  295. _M_check_rehashed(__bucket_count);
  296. }
  297. template<typename _InputIterator>
  298. void
  299. insert(_InputIterator __first, _InputIterator __last)
  300. {
  301. typename __gnu_debug::_Distance_traits<_InputIterator>::__type __dist;
  302. __glibcxx_check_valid_range2(__first, __last, __dist);
  303. size_type __bucket_count = this->bucket_count();
  304. if (__dist.second >= __gnu_debug::__dp_sign)
  305. _Base::insert(__gnu_debug::__unsafe(__first),
  306. __gnu_debug::__unsafe(__last));
  307. else
  308. _Base::insert(__first, __last);
  309. _M_check_rehashed(__bucket_count);
  310. }
  311. #if __cplusplus > 201402L
  312. using node_type = typename _Base::node_type;
  313. using insert_return_type = _Node_insert_return<iterator, node_type>;
  314. node_type
  315. extract(const_iterator __position)
  316. {
  317. __glibcxx_check_erase(__position);
  318. _Base_const_iterator __victim = __position.base();
  319. this->_M_invalidate_if(
  320. [__victim](_Base_const_iterator __it) { return __it == __victim; }
  321. );
  322. this->_M_invalidate_local_if(
  323. [__victim](_Base_const_local_iterator __it) {
  324. return __it._M_curr() == __victim._M_cur;
  325. });
  326. return _Base::extract(__position.base());
  327. }
  328. node_type
  329. extract(const key_type& __key)
  330. {
  331. const auto __position = find(__key);
  332. if (__position != end())
  333. return extract(__position);
  334. return {};
  335. }
  336. insert_return_type
  337. insert(node_type&& __nh)
  338. {
  339. auto __ret = _Base::insert(std::move(__nh));
  340. iterator __pos = iterator(__ret.position, this);
  341. return { __pos, __ret.inserted, std::move(__ret.node) };
  342. }
  343. iterator
  344. insert(const_iterator __hint, node_type&& __nh)
  345. {
  346. __glibcxx_check_insert(__hint);
  347. return iterator(_Base::insert(__hint.base(), std::move(__nh)), this);
  348. }
  349. using _Base::merge;
  350. #endif // C++17
  351. iterator
  352. find(const key_type& __key)
  353. { return iterator(_Base::find(__key), this); }
  354. const_iterator
  355. find(const key_type& __key) const
  356. { return const_iterator(_Base::find(__key), this); }
  357. std::pair<iterator, iterator>
  358. equal_range(const key_type& __key)
  359. {
  360. std::pair<_Base_iterator, _Base_iterator> __res
  361. = _Base::equal_range(__key);
  362. return std::make_pair(iterator(__res.first, this),
  363. iterator(__res.second, this));
  364. }
  365. std::pair<const_iterator, const_iterator>
  366. equal_range(const key_type& __key) const
  367. {
  368. std::pair<_Base_const_iterator, _Base_const_iterator>
  369. __res = _Base::equal_range(__key);
  370. return std::make_pair(const_iterator(__res.first, this),
  371. const_iterator(__res.second, this));
  372. }
  373. size_type
  374. erase(const key_type& __key)
  375. {
  376. size_type __ret(0);
  377. _Base_iterator __victim(_Base::find(__key));
  378. if (__victim != _Base::end())
  379. {
  380. this->_M_invalidate_if(
  381. [__victim](_Base_const_iterator __it)
  382. { return __it == __victim; });
  383. this->_M_invalidate_local_if(
  384. [__victim](_Base_const_local_iterator __it)
  385. { return __it._M_curr() == __victim._M_cur; });
  386. size_type __bucket_count = this->bucket_count();
  387. _Base::erase(__victim);
  388. _M_check_rehashed(__bucket_count);
  389. __ret = 1;
  390. }
  391. return __ret;
  392. }
  393. iterator
  394. erase(const_iterator __it)
  395. {
  396. __glibcxx_check_erase(__it);
  397. _Base_const_iterator __victim = __it.base();
  398. this->_M_invalidate_if(
  399. [__victim](_Base_const_iterator __it)
  400. { return __it == __victim; });
  401. this->_M_invalidate_local_if(
  402. [__victim](_Base_const_local_iterator __it)
  403. { return __it._M_curr() == __victim._M_cur; });
  404. size_type __bucket_count = this->bucket_count();
  405. _Base_iterator __next = _Base::erase(__it.base());
  406. _M_check_rehashed(__bucket_count);
  407. return iterator(__next, this);
  408. }
  409. iterator
  410. erase(iterator __it)
  411. { return erase(const_iterator(__it)); }
  412. iterator
  413. erase(const_iterator __first, const_iterator __last)
  414. {
  415. __glibcxx_check_erase_range(__first, __last);
  416. for (_Base_const_iterator __tmp = __first.base();
  417. __tmp != __last.base(); ++__tmp)
  418. {
  419. _GLIBCXX_DEBUG_VERIFY(__tmp != _Base::end(),
  420. _M_message(__gnu_debug::__msg_valid_range)
  421. ._M_iterator(__first, "first")
  422. ._M_iterator(__last, "last"));
  423. this->_M_invalidate_if(
  424. [__tmp](_Base_const_iterator __it)
  425. { return __it == __tmp; });
  426. this->_M_invalidate_local_if(
  427. [__tmp](_Base_const_local_iterator __it)
  428. { return __it._M_curr() == __tmp._M_cur; });
  429. }
  430. size_type __bucket_count = this->bucket_count();
  431. _Base_iterator __next = _Base::erase(__first.base(),
  432. __last.base());
  433. _M_check_rehashed(__bucket_count);
  434. return iterator(__next, this);
  435. }
  436. _Base&
  437. _M_base() noexcept { return *this; }
  438. const _Base&
  439. _M_base() const noexcept { return *this; }
  440. private:
  441. void
  442. _M_check_rehashed(size_type __prev_count)
  443. {
  444. if (__prev_count != this->bucket_count())
  445. this->_M_invalidate_locals();
  446. }
  447. };
  448. #if __cpp_deduction_guides >= 201606
  449. template<typename _InputIterator,
  450. typename _Hash =
  451. hash<typename iterator_traits<_InputIterator>::value_type>,
  452. typename _Pred =
  453. equal_to<typename iterator_traits<_InputIterator>::value_type>,
  454. typename _Allocator =
  455. allocator<typename iterator_traits<_InputIterator>::value_type>,
  456. typename = _RequireInputIter<_InputIterator>,
  457. typename = _RequireAllocator<_Allocator>>
  458. unordered_set(_InputIterator, _InputIterator,
  459. unordered_set<int>::size_type = {},
  460. _Hash = _Hash(), _Pred = _Pred(), _Allocator = _Allocator())
  461. -> unordered_set<typename iterator_traits<_InputIterator>::value_type,
  462. _Hash, _Pred, _Allocator>;
  463. template<typename _Tp, typename _Hash = hash<_Tp>,
  464. typename _Pred = equal_to<_Tp>,
  465. typename _Allocator = allocator<_Tp>,
  466. typename = _RequireAllocator<_Allocator>>
  467. unordered_set(initializer_list<_Tp>,
  468. unordered_set<int>::size_type = {},
  469. _Hash = _Hash(), _Pred = _Pred(), _Allocator = _Allocator())
  470. -> unordered_set<_Tp, _Hash, _Pred, _Allocator>;
  471. template<typename _InputIterator, typename _Allocator,
  472. typename = _RequireInputIter<_InputIterator>,
  473. typename = _RequireAllocator<_Allocator>>
  474. unordered_set(_InputIterator, _InputIterator,
  475. unordered_set<int>::size_type, _Allocator)
  476. -> unordered_set<typename iterator_traits<_InputIterator>::value_type,
  477. hash<
  478. typename iterator_traits<_InputIterator>::value_type>,
  479. equal_to<
  480. typename iterator_traits<_InputIterator>::value_type>,
  481. _Allocator>;
  482. template<typename _InputIterator, typename _Hash, typename _Allocator,
  483. typename = _RequireInputIter<_InputIterator>,
  484. typename = _RequireAllocator<_Allocator>>
  485. unordered_set(_InputIterator, _InputIterator,
  486. unordered_set<int>::size_type,
  487. _Hash, _Allocator)
  488. -> unordered_set<typename iterator_traits<_InputIterator>::value_type,
  489. _Hash,
  490. equal_to<
  491. typename iterator_traits<_InputIterator>::value_type>,
  492. _Allocator>;
  493. template<typename _Tp, typename _Allocator,
  494. typename = _RequireAllocator<_Allocator>>
  495. unordered_set(initializer_list<_Tp>,
  496. unordered_set<int>::size_type, _Allocator)
  497. -> unordered_set<_Tp, hash<_Tp>, equal_to<_Tp>, _Allocator>;
  498. template<typename _Tp, typename _Hash, typename _Allocator,
  499. typename = _RequireAllocator<_Allocator>>
  500. unordered_set(initializer_list<_Tp>,
  501. unordered_set<int>::size_type, _Hash, _Allocator)
  502. -> unordered_set<_Tp, _Hash, equal_to<_Tp>, _Allocator>;
  503. #endif
  504. template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
  505. inline void
  506. swap(unordered_set<_Value, _Hash, _Pred, _Alloc>& __x,
  507. unordered_set<_Value, _Hash, _Pred, _Alloc>& __y)
  508. noexcept(noexcept(__x.swap(__y)))
  509. { __x.swap(__y); }
  510. template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
  511. inline bool
  512. operator==(const unordered_set<_Value, _Hash, _Pred, _Alloc>& __x,
  513. const unordered_set<_Value, _Hash, _Pred, _Alloc>& __y)
  514. { return __x._M_base() == __y._M_base(); }
  515. template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
  516. inline bool
  517. operator!=(const unordered_set<_Value, _Hash, _Pred, _Alloc>& __x,
  518. const unordered_set<_Value, _Hash, _Pred, _Alloc>& __y)
  519. { return !(__x == __y); }
  520. /// Class std::unordered_multiset with safety/checking/debug instrumentation.
  521. template<typename _Value,
  522. typename _Hash = std::hash<_Value>,
  523. typename _Pred = std::equal_to<_Value>,
  524. typename _Alloc = std::allocator<_Value> >
  525. class unordered_multiset
  526. : public __gnu_debug::_Safe_container<
  527. unordered_multiset<_Value, _Hash, _Pred, _Alloc>, _Alloc,
  528. __gnu_debug::_Safe_unordered_container>,
  529. public _GLIBCXX_STD_C::unordered_multiset<_Value, _Hash, _Pred, _Alloc>
  530. {
  531. typedef _GLIBCXX_STD_C::unordered_multiset<
  532. _Value, _Hash, _Pred, _Alloc> _Base;
  533. typedef __gnu_debug::_Safe_container<unordered_multiset,
  534. _Alloc, __gnu_debug::_Safe_unordered_container> _Safe;
  535. typedef typename _Base::const_iterator _Base_const_iterator;
  536. typedef typename _Base::iterator _Base_iterator;
  537. typedef typename _Base::const_local_iterator
  538. _Base_const_local_iterator;
  539. typedef typename _Base::local_iterator _Base_local_iterator;
  540. public:
  541. typedef typename _Base::size_type size_type;
  542. typedef typename _Base::hasher hasher;
  543. typedef typename _Base::key_equal key_equal;
  544. typedef typename _Base::allocator_type allocator_type;
  545. typedef typename _Base::key_type key_type;
  546. typedef typename _Base::value_type value_type;
  547. typedef __gnu_debug::_Safe_iterator<
  548. _Base_iterator, unordered_multiset> iterator;
  549. typedef __gnu_debug::_Safe_iterator<
  550. _Base_const_iterator, unordered_multiset> const_iterator;
  551. typedef __gnu_debug::_Safe_local_iterator<
  552. _Base_local_iterator, unordered_multiset> local_iterator;
  553. typedef __gnu_debug::_Safe_local_iterator<
  554. _Base_const_local_iterator, unordered_multiset> const_local_iterator;
  555. unordered_multiset() = default;
  556. explicit
  557. unordered_multiset(size_type __n,
  558. const hasher& __hf = hasher(),
  559. const key_equal& __eql = key_equal(),
  560. const allocator_type& __a = allocator_type())
  561. : _Base(__n, __hf, __eql, __a) { }
  562. template<typename _InputIterator>
  563. unordered_multiset(_InputIterator __first, _InputIterator __last,
  564. size_type __n = 0,
  565. const hasher& __hf = hasher(),
  566. const key_equal& __eql = key_equal(),
  567. const allocator_type& __a = allocator_type())
  568. : _Base(__gnu_debug::__base(__gnu_debug::__check_valid_range(__first,
  569. __last)),
  570. __gnu_debug::__base(__last), __n,
  571. __hf, __eql, __a) { }
  572. unordered_multiset(const unordered_multiset&) = default;
  573. unordered_multiset(const _Base& __x)
  574. : _Base(__x) { }
  575. unordered_multiset(unordered_multiset&&) = default;
  576. explicit
  577. unordered_multiset(const allocator_type& __a)
  578. : _Base(__a) { }
  579. unordered_multiset(const unordered_multiset& __uset,
  580. const allocator_type& __a)
  581. : _Base(__uset, __a) { }
  582. unordered_multiset(unordered_multiset&& __uset,
  583. const allocator_type& __a)
  584. : _Safe(std::move(__uset._M_safe()), __a),
  585. _Base(std::move(__uset._M_base()), __a) { }
  586. unordered_multiset(initializer_list<value_type> __l,
  587. size_type __n = 0,
  588. const hasher& __hf = hasher(),
  589. const key_equal& __eql = key_equal(),
  590. const allocator_type& __a = allocator_type())
  591. : _Base(__l, __n, __hf, __eql, __a) { }
  592. unordered_multiset(size_type __n, const allocator_type& __a)
  593. : unordered_multiset(__n, hasher(), key_equal(), __a)
  594. { }
  595. unordered_multiset(size_type __n, const hasher& __hf,
  596. const allocator_type& __a)
  597. : unordered_multiset(__n, __hf, key_equal(), __a)
  598. { }
  599. template<typename _InputIterator>
  600. unordered_multiset(_InputIterator __first, _InputIterator __last,
  601. size_type __n,
  602. const allocator_type& __a)
  603. : unordered_multiset(__first, __last, __n, hasher(), key_equal(), __a)
  604. { }
  605. template<typename _InputIterator>
  606. unordered_multiset(_InputIterator __first, _InputIterator __last,
  607. size_type __n, const hasher& __hf,
  608. const allocator_type& __a)
  609. : unordered_multiset(__first, __last, __n, __hf, key_equal(), __a)
  610. { }
  611. unordered_multiset(initializer_list<value_type> __l,
  612. size_type __n,
  613. const allocator_type& __a)
  614. : unordered_multiset(__l, __n, hasher(), key_equal(), __a)
  615. { }
  616. unordered_multiset(initializer_list<value_type> __l,
  617. size_type __n, const hasher& __hf,
  618. const allocator_type& __a)
  619. : unordered_multiset(__l, __n, __hf, key_equal(), __a)
  620. { }
  621. ~unordered_multiset() = default;
  622. unordered_multiset&
  623. operator=(const unordered_multiset&) = default;
  624. unordered_multiset&
  625. operator=(unordered_multiset&&) = default;
  626. unordered_multiset&
  627. operator=(initializer_list<value_type> __l)
  628. {
  629. this->_M_base() = __l;
  630. this->_M_invalidate_all();
  631. return *this;
  632. }
  633. void
  634. swap(unordered_multiset& __x)
  635. noexcept( noexcept(declval<_Base&>().swap(__x)) )
  636. {
  637. _Safe::_M_swap(__x);
  638. _Base::swap(__x);
  639. }
  640. void
  641. clear() noexcept
  642. {
  643. _Base::clear();
  644. this->_M_invalidate_all();
  645. }
  646. iterator
  647. begin() noexcept
  648. { return iterator(_Base::begin(), this); }
  649. const_iterator
  650. begin() const noexcept
  651. { return const_iterator(_Base::begin(), this); }
  652. iterator
  653. end() noexcept
  654. { return iterator(_Base::end(), this); }
  655. const_iterator
  656. end() const noexcept
  657. { return const_iterator(_Base::end(), this); }
  658. const_iterator
  659. cbegin() const noexcept
  660. { return const_iterator(_Base::begin(), this); }
  661. const_iterator
  662. cend() const noexcept
  663. { return const_iterator(_Base::end(), this); }
  664. // local versions
  665. local_iterator
  666. begin(size_type __b)
  667. {
  668. __glibcxx_check_bucket_index(__b);
  669. return local_iterator(_Base::begin(__b), this);
  670. }
  671. local_iterator
  672. end(size_type __b)
  673. {
  674. __glibcxx_check_bucket_index(__b);
  675. return local_iterator(_Base::end(__b), this);
  676. }
  677. const_local_iterator
  678. begin(size_type __b) const
  679. {
  680. __glibcxx_check_bucket_index(__b);
  681. return const_local_iterator(_Base::begin(__b), this);
  682. }
  683. const_local_iterator
  684. end(size_type __b) const
  685. {
  686. __glibcxx_check_bucket_index(__b);
  687. return const_local_iterator(_Base::end(__b), this);
  688. }
  689. const_local_iterator
  690. cbegin(size_type __b) const
  691. {
  692. __glibcxx_check_bucket_index(__b);
  693. return const_local_iterator(_Base::cbegin(__b), this);
  694. }
  695. const_local_iterator
  696. cend(size_type __b) const
  697. {
  698. __glibcxx_check_bucket_index(__b);
  699. return const_local_iterator(_Base::cend(__b), this);
  700. }
  701. size_type
  702. bucket_size(size_type __b) const
  703. {
  704. __glibcxx_check_bucket_index(__b);
  705. return _Base::bucket_size(__b);
  706. }
  707. float
  708. max_load_factor() const noexcept
  709. { return _Base::max_load_factor(); }
  710. void
  711. max_load_factor(float __f)
  712. {
  713. __glibcxx_check_max_load_factor(__f);
  714. _Base::max_load_factor(__f);
  715. }
  716. template<typename... _Args>
  717. iterator
  718. emplace(_Args&&... __args)
  719. {
  720. size_type __bucket_count = this->bucket_count();
  721. _Base_iterator __it
  722. = _Base::emplace(std::forward<_Args>(__args)...);
  723. _M_check_rehashed(__bucket_count);
  724. return iterator(__it, this);
  725. }
  726. template<typename... _Args>
  727. iterator
  728. emplace_hint(const_iterator __hint, _Args&&... __args)
  729. {
  730. __glibcxx_check_insert(__hint);
  731. size_type __bucket_count = this->bucket_count();
  732. _Base_iterator __it = _Base::emplace_hint(__hint.base(),
  733. std::forward<_Args>(__args)...);
  734. _M_check_rehashed(__bucket_count);
  735. return iterator(__it, this);
  736. }
  737. iterator
  738. insert(const value_type& __obj)
  739. {
  740. size_type __bucket_count = this->bucket_count();
  741. _Base_iterator __it = _Base::insert(__obj);
  742. _M_check_rehashed(__bucket_count);
  743. return iterator(__it, this);
  744. }
  745. iterator
  746. insert(const_iterator __hint, const value_type& __obj)
  747. {
  748. __glibcxx_check_insert(__hint);
  749. size_type __bucket_count = this->bucket_count();
  750. _Base_iterator __it = _Base::insert(__hint.base(), __obj);
  751. _M_check_rehashed(__bucket_count);
  752. return iterator(__it, this);
  753. }
  754. iterator
  755. insert(value_type&& __obj)
  756. {
  757. size_type __bucket_count = this->bucket_count();
  758. _Base_iterator __it = _Base::insert(std::move(__obj));
  759. _M_check_rehashed(__bucket_count);
  760. return iterator(__it, this);
  761. }
  762. iterator
  763. insert(const_iterator __hint, value_type&& __obj)
  764. {
  765. __glibcxx_check_insert(__hint);
  766. size_type __bucket_count = this->bucket_count();
  767. _Base_iterator __it = _Base::insert(__hint.base(), std::move(__obj));
  768. _M_check_rehashed(__bucket_count);
  769. return iterator(__it, this);
  770. }
  771. void
  772. insert(std::initializer_list<value_type> __l)
  773. {
  774. size_type __bucket_count = this->bucket_count();
  775. _Base::insert(__l);
  776. _M_check_rehashed(__bucket_count);
  777. }
  778. template<typename _InputIterator>
  779. void
  780. insert(_InputIterator __first, _InputIterator __last)
  781. {
  782. typename __gnu_debug::_Distance_traits<_InputIterator>::__type __dist;
  783. __glibcxx_check_valid_range2(__first, __last, __dist);
  784. size_type __bucket_count = this->bucket_count();
  785. if (__dist.second >= __gnu_debug::__dp_sign)
  786. _Base::insert(__gnu_debug::__unsafe(__first),
  787. __gnu_debug::__unsafe(__last));
  788. else
  789. _Base::insert(__first, __last);
  790. _M_check_rehashed(__bucket_count);
  791. }
  792. #if __cplusplus > 201402L
  793. using node_type = typename _Base::node_type;
  794. node_type
  795. extract(const_iterator __position)
  796. {
  797. __glibcxx_check_erase(__position);
  798. _Base_const_iterator __victim = __position.base();
  799. this->_M_invalidate_if(
  800. [__victim](_Base_const_iterator __it) { return __it == __victim; }
  801. );
  802. this->_M_invalidate_local_if(
  803. [__victim](_Base_const_local_iterator __it) {
  804. return __it._M_curr() == __victim._M_cur;
  805. });
  806. return _Base::extract(__position.base());
  807. }
  808. node_type
  809. extract(const key_type& __key)
  810. {
  811. const auto __position = find(__key);
  812. if (__position != end())
  813. return extract(__position);
  814. return {};
  815. }
  816. iterator
  817. insert(node_type&& __nh)
  818. { return iterator(_Base::insert(std::move(__nh)), this); }
  819. iterator
  820. insert(const_iterator __hint, node_type&& __nh)
  821. {
  822. __glibcxx_check_insert(__hint);
  823. return iterator(_Base::insert(__hint.base(), std::move(__nh)), this);
  824. }
  825. using _Base::merge;
  826. #endif // C++17
  827. iterator
  828. find(const key_type& __key)
  829. { return iterator(_Base::find(__key), this); }
  830. const_iterator
  831. find(const key_type& __key) const
  832. { return const_iterator(_Base::find(__key), this); }
  833. std::pair<iterator, iterator>
  834. equal_range(const key_type& __key)
  835. {
  836. std::pair<_Base_iterator, _Base_iterator> __res
  837. = _Base::equal_range(__key);
  838. return std::make_pair(iterator(__res.first, this),
  839. iterator(__res.second, this));
  840. }
  841. std::pair<const_iterator, const_iterator>
  842. equal_range(const key_type& __key) const
  843. {
  844. std::pair<_Base_const_iterator, _Base_const_iterator>
  845. __res = _Base::equal_range(__key);
  846. return std::make_pair(const_iterator(__res.first, this),
  847. const_iterator(__res.second, this));
  848. }
  849. size_type
  850. erase(const key_type& __key)
  851. {
  852. size_type __ret(0);
  853. std::pair<_Base_iterator, _Base_iterator> __pair =
  854. _Base::equal_range(__key);
  855. for (_Base_iterator __victim = __pair.first; __victim != __pair.second;)
  856. {
  857. this->_M_invalidate_if([__victim](_Base_const_iterator __it)
  858. { return __it == __victim; });
  859. this->_M_invalidate_local_if(
  860. [__victim](_Base_const_local_iterator __it)
  861. { return __it._M_curr() == __victim._M_cur; });
  862. _Base::erase(__victim++);
  863. ++__ret;
  864. }
  865. return __ret;
  866. }
  867. iterator
  868. erase(const_iterator __it)
  869. {
  870. __glibcxx_check_erase(__it);
  871. _Base_const_iterator __victim = __it.base();
  872. this->_M_invalidate_if([__victim](_Base_const_iterator __it)
  873. { return __it == __victim; });
  874. this->_M_invalidate_local_if(
  875. [__victim](_Base_const_local_iterator __it)
  876. { return __it._M_curr() == __victim._M_cur; });
  877. return iterator(_Base::erase(__it.base()), this);
  878. }
  879. iterator
  880. erase(iterator __it)
  881. { return erase(const_iterator(__it)); }
  882. iterator
  883. erase(const_iterator __first, const_iterator __last)
  884. {
  885. __glibcxx_check_erase_range(__first, __last);
  886. for (_Base_const_iterator __tmp = __first.base();
  887. __tmp != __last.base(); ++__tmp)
  888. {
  889. _GLIBCXX_DEBUG_VERIFY(__tmp != _Base::end(),
  890. _M_message(__gnu_debug::__msg_valid_range)
  891. ._M_iterator(__first, "first")
  892. ._M_iterator(__last, "last"));
  893. this->_M_invalidate_if([__tmp](_Base_const_iterator __it)
  894. { return __it == __tmp; });
  895. this->_M_invalidate_local_if(
  896. [__tmp](_Base_const_local_iterator __it)
  897. { return __it._M_curr() == __tmp._M_cur; });
  898. }
  899. return iterator(_Base::erase(__first.base(),
  900. __last.base()), this);
  901. }
  902. _Base&
  903. _M_base() noexcept { return *this; }
  904. const _Base&
  905. _M_base() const noexcept { return *this; }
  906. private:
  907. void
  908. _M_check_rehashed(size_type __prev_count)
  909. {
  910. if (__prev_count != this->bucket_count())
  911. this->_M_invalidate_locals();
  912. }
  913. };
  914. #if __cpp_deduction_guides >= 201606
  915. template<typename _InputIterator,
  916. typename _Hash =
  917. hash<typename iterator_traits<_InputIterator>::value_type>,
  918. typename _Pred =
  919. equal_to<typename iterator_traits<_InputIterator>::value_type>,
  920. typename _Allocator =
  921. allocator<typename iterator_traits<_InputIterator>::value_type>,
  922. typename = _RequireInputIter<_InputIterator>,
  923. typename = _RequireAllocator<_Allocator>>
  924. unordered_multiset(_InputIterator, _InputIterator,
  925. unordered_multiset<int>::size_type = {},
  926. _Hash = _Hash(), _Pred = _Pred(),
  927. _Allocator = _Allocator())
  928. -> unordered_multiset<typename iterator_traits<_InputIterator>::value_type,
  929. _Hash, _Pred, _Allocator>;
  930. template<typename _Tp, typename _Hash = hash<_Tp>,
  931. typename _Pred = equal_to<_Tp>,
  932. typename _Allocator = allocator<_Tp>,
  933. typename = _RequireAllocator<_Allocator>>
  934. unordered_multiset(initializer_list<_Tp>,
  935. unordered_multiset<int>::size_type = {},
  936. _Hash = _Hash(), _Pred = _Pred(),
  937. _Allocator = _Allocator())
  938. -> unordered_multiset<_Tp, _Hash, _Pred, _Allocator>;
  939. template<typename _InputIterator, typename _Allocator,
  940. typename = _RequireInputIter<_InputIterator>,
  941. typename = _RequireAllocator<_Allocator>>
  942. unordered_multiset(_InputIterator, _InputIterator,
  943. unordered_multiset<int>::size_type, _Allocator)
  944. -> unordered_multiset<typename iterator_traits<_InputIterator>::value_type,
  945. hash<typename
  946. iterator_traits<_InputIterator>::value_type>,
  947. equal_to<typename
  948. iterator_traits<_InputIterator>::value_type>,
  949. _Allocator>;
  950. template<typename _InputIterator, typename _Hash, typename _Allocator,
  951. typename = _RequireInputIter<_InputIterator>,
  952. typename = _RequireAllocator<_Allocator>>
  953. unordered_multiset(_InputIterator, _InputIterator,
  954. unordered_multiset<int>::size_type,
  955. _Hash, _Allocator)
  956. -> unordered_multiset<typename
  957. iterator_traits<_InputIterator>::value_type,
  958. _Hash,
  959. equal_to<
  960. typename
  961. iterator_traits<_InputIterator>::value_type>,
  962. _Allocator>;
  963. template<typename _Tp, typename _Allocator,
  964. typename = _RequireAllocator<_Allocator>>
  965. unordered_multiset(initializer_list<_Tp>,
  966. unordered_multiset<int>::size_type, _Allocator)
  967. -> unordered_multiset<_Tp, hash<_Tp>, equal_to<_Tp>, _Allocator>;
  968. template<typename _Tp, typename _Hash, typename _Allocator,
  969. typename = _RequireAllocator<_Allocator>>
  970. unordered_multiset(initializer_list<_Tp>,
  971. unordered_multiset<int>::size_type, _Hash, _Allocator)
  972. -> unordered_multiset<_Tp, _Hash, equal_to<_Tp>, _Allocator>;
  973. #endif
  974. template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
  975. inline void
  976. swap(unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __x,
  977. unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __y)
  978. noexcept(noexcept(__x.swap(__y)))
  979. { __x.swap(__y); }
  980. template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
  981. inline bool
  982. operator==(const unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __x,
  983. const unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __y)
  984. { return __x._M_base() == __y._M_base(); }
  985. template<typename _Value, typename _Hash, typename _Pred, typename _Alloc>
  986. inline bool
  987. operator!=(const unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __x,
  988. const unordered_multiset<_Value, _Hash, _Pred, _Alloc>& __y)
  989. { return !(__x == __y); }
  990. } // namespace __debug
  991. } // namespace std
  992. #endif // C++11
  993. #endif