libstdc++
|
00001 // Debugging map implementation -*- C++ -*- 00002 00003 // Copyright (C) 2003-2017 Free Software Foundation, Inc. 00004 // 00005 // This file is part of the GNU ISO C++ Library. This library is free 00006 // software; you can redistribute it and/or modify it under the 00007 // terms of the GNU General Public License as published by the 00008 // Free Software Foundation; either version 3, or (at your option) 00009 // any later version. 00010 00011 // This library is distributed in the hope that it will be useful, 00012 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00014 // GNU General Public License for more details. 00015 00016 // Under Section 7 of GPL version 3, you are granted additional 00017 // permissions described in the GCC Runtime Library Exception, version 00018 // 3.1, as published by the Free Software Foundation. 00019 00020 // You should have received a copy of the GNU General Public License and 00021 // a copy of the GCC Runtime Library Exception along with this program; 00022 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 00023 // <http://www.gnu.org/licenses/>. 00024 00025 /** @file debug/map.h 00026 * This file is a GNU debug extension to the Standard C++ Library. 00027 */ 00028 00029 #ifndef _GLIBCXX_DEBUG_MAP_H 00030 #define _GLIBCXX_DEBUG_MAP_H 1 00031 00032 #include <debug/safe_sequence.h> 00033 #include <debug/safe_container.h> 00034 #include <debug/safe_iterator.h> 00035 #include <utility> 00036 00037 namespace std _GLIBCXX_VISIBILITY(default) 00038 { 00039 namespace __debug 00040 { 00041 /// Class std::map with safety/checking/debug instrumentation. 00042 template<typename _Key, typename _Tp, typename _Compare = std::less<_Key>, 00043 typename _Allocator = std::allocator<std::pair<const _Key, _Tp> > > 00044 class map 00045 : public __gnu_debug::_Safe_container< 00046 map<_Key, _Tp, _Compare, _Allocator>, _Allocator, 00047 __gnu_debug::_Safe_node_sequence>, 00048 public _GLIBCXX_STD_C::map<_Key, _Tp, _Compare, _Allocator> 00049 { 00050 typedef _GLIBCXX_STD_C::map< 00051 _Key, _Tp, _Compare, _Allocator> _Base; 00052 typedef __gnu_debug::_Safe_container< 00053 map, _Allocator, __gnu_debug::_Safe_node_sequence> _Safe; 00054 00055 typedef typename _Base::const_iterator _Base_const_iterator; 00056 typedef typename _Base::iterator _Base_iterator; 00057 typedef __gnu_debug::_Equal_to<_Base_const_iterator> _Equal; 00058 00059 public: 00060 // types: 00061 typedef _Key key_type; 00062 typedef _Tp mapped_type; 00063 typedef std::pair<const _Key, _Tp> value_type; 00064 typedef _Compare key_compare; 00065 typedef _Allocator allocator_type; 00066 typedef typename _Base::reference reference; 00067 typedef typename _Base::const_reference const_reference; 00068 00069 typedef __gnu_debug::_Safe_iterator<_Base_iterator, map> 00070 iterator; 00071 typedef __gnu_debug::_Safe_iterator<_Base_const_iterator, map> 00072 const_iterator; 00073 00074 typedef typename _Base::size_type size_type; 00075 typedef typename _Base::difference_type difference_type; 00076 typedef typename _Base::pointer pointer; 00077 typedef typename _Base::const_pointer const_pointer; 00078 typedef std::reverse_iterator<iterator> reverse_iterator; 00079 typedef std::reverse_iterator<const_iterator> const_reverse_iterator; 00080 00081 // 23.3.1.1 construct/copy/destroy: 00082 00083 #if __cplusplus < 201103L 00084 map() : _Base() { } 00085 00086 map(const map& __x) 00087 : _Base(__x) { } 00088 00089 ~map() { } 00090 #else 00091 map() = default; 00092 map(const map&) = default; 00093 map(map&&) = default; 00094 00095 map(initializer_list<value_type> __l, 00096 const _Compare& __c = _Compare(), 00097 const allocator_type& __a = allocator_type()) 00098 : _Base(__l, __c, __a) { } 00099 00100 explicit 00101 map(const allocator_type& __a) 00102 : _Base(__a) { } 00103 00104 map(const map& __m, const allocator_type& __a) 00105 : _Base(__m, __a) { } 00106 00107 map(map&& __m, const allocator_type& __a) 00108 : _Safe(std::move(__m._M_safe()), __a), 00109 _Base(std::move(__m._M_base()), __a) { } 00110 00111 map(initializer_list<value_type> __l, const allocator_type& __a) 00112 : _Base(__l, __a) { } 00113 00114 template<typename _InputIterator> 00115 map(_InputIterator __first, _InputIterator __last, 00116 const allocator_type& __a) 00117 : _Base(__gnu_debug::__base(__gnu_debug::__check_valid_range(__first, 00118 __last)), 00119 __gnu_debug::__base(__last), __a) 00120 { } 00121 00122 ~map() = default; 00123 #endif 00124 00125 map(const _Base& __x) 00126 : _Base(__x) { } 00127 00128 explicit map(const _Compare& __comp, 00129 const _Allocator& __a = _Allocator()) 00130 : _Base(__comp, __a) { } 00131 00132 template<typename _InputIterator> 00133 map(_InputIterator __first, _InputIterator __last, 00134 const _Compare& __comp = _Compare(), 00135 const _Allocator& __a = _Allocator()) 00136 : _Base(__gnu_debug::__base(__gnu_debug::__check_valid_range(__first, 00137 __last)), 00138 __gnu_debug::__base(__last), 00139 __comp, __a) { } 00140 00141 #if __cplusplus < 201103L 00142 map& 00143 operator=(const map& __x) 00144 { 00145 this->_M_safe() = __x; 00146 _M_base() = __x; 00147 return *this; 00148 } 00149 #else 00150 map& 00151 operator=(const map&) = default; 00152 00153 map& 00154 operator=(map&&) = default; 00155 00156 map& 00157 operator=(initializer_list<value_type> __l) 00158 { 00159 _M_base() = __l; 00160 this->_M_invalidate_all(); 00161 return *this; 00162 } 00163 #endif 00164 00165 // _GLIBCXX_RESOLVE_LIB_DEFECTS 00166 // 133. map missing get_allocator() 00167 using _Base::get_allocator; 00168 00169 // iterators: 00170 iterator 00171 begin() _GLIBCXX_NOEXCEPT 00172 { return iterator(_Base::begin(), this); } 00173 00174 const_iterator 00175 begin() const _GLIBCXX_NOEXCEPT 00176 { return const_iterator(_Base::begin(), this); } 00177 00178 iterator 00179 end() _GLIBCXX_NOEXCEPT 00180 { return iterator(_Base::end(), this); } 00181 00182 const_iterator 00183 end() const _GLIBCXX_NOEXCEPT 00184 { return const_iterator(_Base::end(), this); } 00185 00186 reverse_iterator 00187 rbegin() _GLIBCXX_NOEXCEPT 00188 { return reverse_iterator(end()); } 00189 00190 const_reverse_iterator 00191 rbegin() const _GLIBCXX_NOEXCEPT 00192 { return const_reverse_iterator(end()); } 00193 00194 reverse_iterator 00195 rend() _GLIBCXX_NOEXCEPT 00196 { return reverse_iterator(begin()); } 00197 00198 const_reverse_iterator 00199 rend() const _GLIBCXX_NOEXCEPT 00200 { return const_reverse_iterator(begin()); } 00201 00202 #if __cplusplus >= 201103L 00203 const_iterator 00204 cbegin() const noexcept 00205 { return const_iterator(_Base::begin(), this); } 00206 00207 const_iterator 00208 cend() const noexcept 00209 { return const_iterator(_Base::end(), this); } 00210 00211 const_reverse_iterator 00212 crbegin() const noexcept 00213 { return const_reverse_iterator(end()); } 00214 00215 const_reverse_iterator 00216 crend() const noexcept 00217 { return const_reverse_iterator(begin()); } 00218 #endif 00219 00220 // capacity: 00221 using _Base::empty; 00222 using _Base::size; 00223 using _Base::max_size; 00224 00225 // 23.3.1.2 element access: 00226 using _Base::operator[]; 00227 00228 // _GLIBCXX_RESOLVE_LIB_DEFECTS 00229 // DR 464. Suggestion for new member functions in standard containers. 00230 using _Base::at; 00231 00232 // modifiers: 00233 #if __cplusplus >= 201103L 00234 template<typename... _Args> 00235 std::pair<iterator, bool> 00236 emplace(_Args&&... __args) 00237 { 00238 auto __res = _Base::emplace(std::forward<_Args>(__args)...); 00239 return std::pair<iterator, bool>(iterator(__res.first, this), 00240 __res.second); 00241 } 00242 00243 template<typename... _Args> 00244 iterator 00245 emplace_hint(const_iterator __pos, _Args&&... __args) 00246 { 00247 __glibcxx_check_insert(__pos); 00248 return iterator(_Base::emplace_hint(__pos.base(), 00249 std::forward<_Args>(__args)...), 00250 this); 00251 } 00252 #endif 00253 00254 std::pair<iterator, bool> 00255 insert(const value_type& __x) 00256 { 00257 std::pair<_Base_iterator, bool> __res = _Base::insert(__x); 00258 return std::pair<iterator, bool>(iterator(__res.first, this), 00259 __res.second); 00260 } 00261 00262 #if __cplusplus >= 201103L 00263 // _GLIBCXX_RESOLVE_LIB_DEFECTS 00264 // 2354. Unnecessary copying when inserting into maps with braced-init 00265 std::pair<iterator, bool> 00266 insert(value_type&& __x) 00267 { 00268 auto __res = _Base::insert(std::move(__x)); 00269 return { iterator(__res.first, this), __res.second }; 00270 } 00271 00272 template<typename _Pair, typename = typename 00273 std::enable_if<std::is_constructible<value_type, 00274 _Pair&&>::value>::type> 00275 std::pair<iterator, bool> 00276 insert(_Pair&& __x) 00277 { 00278 std::pair<_Base_iterator, bool> __res 00279 = _Base::insert(std::forward<_Pair>(__x)); 00280 return std::pair<iterator, bool>(iterator(__res.first, this), 00281 __res.second); 00282 } 00283 #endif 00284 00285 #if __cplusplus >= 201103L 00286 void 00287 insert(std::initializer_list<value_type> __list) 00288 { _Base::insert(__list); } 00289 #endif 00290 00291 iterator 00292 #if __cplusplus >= 201103L 00293 insert(const_iterator __position, const value_type& __x) 00294 #else 00295 insert(iterator __position, const value_type& __x) 00296 #endif 00297 { 00298 __glibcxx_check_insert(__position); 00299 return iterator(_Base::insert(__position.base(), __x), this); 00300 } 00301 00302 #if __cplusplus >= 201103L 00303 // _GLIBCXX_RESOLVE_LIB_DEFECTS 00304 // 2354. Unnecessary copying when inserting into maps with braced-init 00305 iterator 00306 insert(const_iterator __position, value_type&& __x) 00307 { 00308 __glibcxx_check_insert(__position); 00309 return { _Base::insert(__position.base(), std::move(__x)), this }; 00310 } 00311 00312 template<typename _Pair, typename = typename 00313 std::enable_if<std::is_constructible<value_type, 00314 _Pair&&>::value>::type> 00315 iterator 00316 insert(const_iterator __position, _Pair&& __x) 00317 { 00318 __glibcxx_check_insert(__position); 00319 return iterator(_Base::insert(__position.base(), 00320 std::forward<_Pair>(__x)), this); 00321 } 00322 #endif 00323 00324 template<typename _InputIterator> 00325 void 00326 insert(_InputIterator __first, _InputIterator __last) 00327 { 00328 typename __gnu_debug::_Distance_traits<_InputIterator>::__type __dist; 00329 __glibcxx_check_valid_range2(__first, __last, __dist); 00330 00331 if (__dist.second >= __gnu_debug::__dp_sign) 00332 _Base::insert(__gnu_debug::__unsafe(__first), 00333 __gnu_debug::__unsafe(__last)); 00334 else 00335 _Base::insert(__first, __last); 00336 } 00337 00338 00339 #if __cplusplus > 201402L 00340 template <typename... _Args> 00341 pair<iterator, bool> 00342 try_emplace(const key_type& __k, _Args&&... __args) 00343 { 00344 auto __res = _Base::try_emplace(__k, 00345 std::forward<_Args>(__args)...); 00346 return { iterator(__res.first, this), __res.second }; 00347 } 00348 00349 template <typename... _Args> 00350 pair<iterator, bool> 00351 try_emplace(key_type&& __k, _Args&&... __args) 00352 { 00353 auto __res = _Base::try_emplace(std::move(__k), 00354 std::forward<_Args>(__args)...); 00355 return { iterator(__res.first, this), __res.second }; 00356 } 00357 00358 template <typename... _Args> 00359 iterator 00360 try_emplace(const_iterator __hint, const key_type& __k, 00361 _Args&&... __args) 00362 { 00363 __glibcxx_check_insert(__hint); 00364 return iterator(_Base::try_emplace(__hint.base(), __k, 00365 std::forward<_Args>(__args)...), 00366 this); 00367 } 00368 00369 template <typename... _Args> 00370 iterator 00371 try_emplace(const_iterator __hint, key_type&& __k, _Args&&... __args) 00372 { 00373 __glibcxx_check_insert(__hint); 00374 return iterator(_Base::try_emplace(__hint.base(), std::move(__k), 00375 std::forward<_Args>(__args)...), 00376 this); 00377 } 00378 00379 template <typename _Obj> 00380 std::pair<iterator, bool> 00381 insert_or_assign(const key_type& __k, _Obj&& __obj) 00382 { 00383 auto __res = _Base::insert_or_assign(__k, 00384 std::forward<_Obj>(__obj)); 00385 return { iterator(__res.first, this), __res.second }; 00386 } 00387 00388 template <typename _Obj> 00389 std::pair<iterator, bool> 00390 insert_or_assign(key_type&& __k, _Obj&& __obj) 00391 { 00392 auto __res = _Base::insert_or_assign(std::move(__k), 00393 std::forward<_Obj>(__obj)); 00394 return { iterator(__res.first, this), __res.second }; 00395 } 00396 00397 template <typename _Obj> 00398 iterator 00399 insert_or_assign(const_iterator __hint, 00400 const key_type& __k, _Obj&& __obj) 00401 { 00402 __glibcxx_check_insert(__hint); 00403 return iterator(_Base::insert_or_assign(__hint.base(), __k, 00404 std::forward<_Obj>(__obj)), 00405 this); 00406 } 00407 00408 template <typename _Obj> 00409 iterator 00410 insert_or_assign(const_iterator __hint, key_type&& __k, _Obj&& __obj) 00411 { 00412 __glibcxx_check_insert(__hint); 00413 return iterator(_Base::insert_or_assign(__hint.base(), 00414 std::move(__k), 00415 std::forward<_Obj>(__obj)), 00416 this); 00417 } 00418 #endif // C++17 00419 00420 #if __cplusplus > 201402L 00421 using node_type = typename _Base::node_type; 00422 00423 struct insert_return_type 00424 { 00425 bool inserted; 00426 iterator position; 00427 node_type node; 00428 }; 00429 00430 node_type 00431 extract(const_iterator __position) 00432 { 00433 __glibcxx_check_erase(__position); 00434 this->_M_invalidate_if(_Equal(__position.base())); 00435 return _Base::extract(__position.base()); 00436 } 00437 00438 node_type 00439 extract(const key_type& __key) 00440 { 00441 const auto __position = find(__key); 00442 if (__position != end()) 00443 return extract(__position); 00444 return {}; 00445 } 00446 00447 insert_return_type 00448 insert(node_type&& __nh) 00449 { 00450 auto __ret = _Base::insert(std::move(__nh)); 00451 iterator __pos = iterator(__ret.position, this); 00452 return { __ret.inserted, __pos, std::move(__ret.node) }; 00453 } 00454 00455 iterator 00456 insert(const_iterator __hint, node_type&& __nh) 00457 { 00458 __glibcxx_check_insert(__hint); 00459 return iterator(_Base::insert(__hint.base(), std::move(__nh)), this); 00460 } 00461 00462 using _Base::merge; 00463 #endif // C++17 00464 00465 #if __cplusplus >= 201103L 00466 iterator 00467 erase(const_iterator __position) 00468 { 00469 __glibcxx_check_erase(__position); 00470 this->_M_invalidate_if(_Equal(__position.base())); 00471 return iterator(_Base::erase(__position.base()), this); 00472 } 00473 00474 iterator 00475 erase(iterator __position) 00476 { return erase(const_iterator(__position)); } 00477 #else 00478 void 00479 erase(iterator __position) 00480 { 00481 __glibcxx_check_erase(__position); 00482 this->_M_invalidate_if(_Equal(__position.base())); 00483 _Base::erase(__position.base()); 00484 } 00485 #endif 00486 00487 size_type 00488 erase(const key_type& __x) 00489 { 00490 _Base_iterator __victim = _Base::find(__x); 00491 if (__victim == _Base::end()) 00492 return 0; 00493 else 00494 { 00495 this->_M_invalidate_if(_Equal(__victim)); 00496 _Base::erase(__victim); 00497 return 1; 00498 } 00499 } 00500 00501 #if __cplusplus >= 201103L 00502 iterator 00503 erase(const_iterator __first, const_iterator __last) 00504 { 00505 // _GLIBCXX_RESOLVE_LIB_DEFECTS 00506 // 151. can't currently clear() empty container 00507 __glibcxx_check_erase_range(__first, __last); 00508 for (_Base_const_iterator __victim = __first.base(); 00509 __victim != __last.base(); ++__victim) 00510 { 00511 _GLIBCXX_DEBUG_VERIFY(__victim != _Base::end(), 00512 _M_message(__gnu_debug::__msg_valid_range) 00513 ._M_iterator(__first, "first") 00514 ._M_iterator(__last, "last")); 00515 this->_M_invalidate_if(_Equal(__victim)); 00516 } 00517 return iterator(_Base::erase(__first.base(), __last.base()), this); 00518 } 00519 #else 00520 void 00521 erase(iterator __first, iterator __last) 00522 { 00523 // _GLIBCXX_RESOLVE_LIB_DEFECTS 00524 // 151. can't currently clear() empty container 00525 __glibcxx_check_erase_range(__first, __last); 00526 for (_Base_iterator __victim = __first.base(); 00527 __victim != __last.base(); ++__victim) 00528 { 00529 _GLIBCXX_DEBUG_VERIFY(__victim != _Base::end(), 00530 _M_message(__gnu_debug::__msg_valid_range) 00531 ._M_iterator(__first, "first") 00532 ._M_iterator(__last, "last")); 00533 this->_M_invalidate_if(_Equal(__victim)); 00534 } 00535 _Base::erase(__first.base(), __last.base()); 00536 } 00537 #endif 00538 00539 void 00540 swap(map& __x) 00541 _GLIBCXX_NOEXCEPT_IF( noexcept(declval<_Base&>().swap(__x)) ) 00542 { 00543 _Safe::_M_swap(__x); 00544 _Base::swap(__x); 00545 } 00546 00547 void 00548 clear() _GLIBCXX_NOEXCEPT 00549 { 00550 this->_M_invalidate_all(); 00551 _Base::clear(); 00552 } 00553 00554 // observers: 00555 using _Base::key_comp; 00556 using _Base::value_comp; 00557 00558 // 23.3.1.3 map operations: 00559 iterator 00560 find(const key_type& __x) 00561 { return iterator(_Base::find(__x), this); } 00562 00563 #if __cplusplus > 201103L 00564 template<typename _Kt, 00565 typename _Req = 00566 typename __has_is_transparent<_Compare, _Kt>::type> 00567 iterator 00568 find(const _Kt& __x) 00569 { return { _Base::find(__x), this }; } 00570 #endif 00571 00572 const_iterator 00573 find(const key_type& __x) const 00574 { return const_iterator(_Base::find(__x), this); } 00575 00576 #if __cplusplus > 201103L 00577 template<typename _Kt, 00578 typename _Req = 00579 typename __has_is_transparent<_Compare, _Kt>::type> 00580 const_iterator 00581 find(const _Kt& __x) const 00582 { return { _Base::find(__x), this }; } 00583 #endif 00584 00585 using _Base::count; 00586 00587 iterator 00588 lower_bound(const key_type& __x) 00589 { return iterator(_Base::lower_bound(__x), this); } 00590 00591 #if __cplusplus > 201103L 00592 template<typename _Kt, 00593 typename _Req = 00594 typename __has_is_transparent<_Compare, _Kt>::type> 00595 iterator 00596 lower_bound(const _Kt& __x) 00597 { return { _Base::lower_bound(__x), this }; } 00598 #endif 00599 00600 const_iterator 00601 lower_bound(const key_type& __x) const 00602 { return const_iterator(_Base::lower_bound(__x), this); } 00603 00604 #if __cplusplus > 201103L 00605 template<typename _Kt, 00606 typename _Req = 00607 typename __has_is_transparent<_Compare, _Kt>::type> 00608 const_iterator 00609 lower_bound(const _Kt& __x) const 00610 { return { _Base::lower_bound(__x), this }; } 00611 #endif 00612 00613 iterator 00614 upper_bound(const key_type& __x) 00615 { return iterator(_Base::upper_bound(__x), this); } 00616 00617 #if __cplusplus > 201103L 00618 template<typename _Kt, 00619 typename _Req = 00620 typename __has_is_transparent<_Compare, _Kt>::type> 00621 iterator 00622 upper_bound(const _Kt& __x) 00623 { return { _Base::upper_bound(__x), this }; } 00624 #endif 00625 00626 const_iterator 00627 upper_bound(const key_type& __x) const 00628 { return const_iterator(_Base::upper_bound(__x), this); } 00629 00630 #if __cplusplus > 201103L 00631 template<typename _Kt, 00632 typename _Req = 00633 typename __has_is_transparent<_Compare, _Kt>::type> 00634 const_iterator 00635 upper_bound(const _Kt& __x) const 00636 { return { _Base::upper_bound(__x), this }; } 00637 #endif 00638 00639 std::pair<iterator,iterator> 00640 equal_range(const key_type& __x) 00641 { 00642 std::pair<_Base_iterator, _Base_iterator> __res = 00643 _Base::equal_range(__x); 00644 return std::make_pair(iterator(__res.first, this), 00645 iterator(__res.second, this)); 00646 } 00647 00648 #if __cplusplus > 201103L 00649 template<typename _Kt, 00650 typename _Req = 00651 typename __has_is_transparent<_Compare, _Kt>::type> 00652 std::pair<iterator, iterator> 00653 equal_range(const _Kt& __x) 00654 { 00655 auto __res = _Base::equal_range(__x); 00656 return { { __res.first, this }, { __res.second, this } }; 00657 } 00658 #endif 00659 00660 std::pair<const_iterator,const_iterator> 00661 equal_range(const key_type& __x) const 00662 { 00663 std::pair<_Base_const_iterator, _Base_const_iterator> __res = 00664 _Base::equal_range(__x); 00665 return std::make_pair(const_iterator(__res.first, this), 00666 const_iterator(__res.second, this)); 00667 } 00668 00669 #if __cplusplus > 201103L 00670 template<typename _Kt, 00671 typename _Req = 00672 typename __has_is_transparent<_Compare, _Kt>::type> 00673 std::pair<const_iterator, const_iterator> 00674 equal_range(const _Kt& __x) const 00675 { 00676 auto __res = _Base::equal_range(__x); 00677 return { { __res.first, this }, { __res.second, this } }; 00678 } 00679 #endif 00680 00681 _Base& 00682 _M_base() _GLIBCXX_NOEXCEPT { return *this; } 00683 00684 const _Base& 00685 _M_base() const _GLIBCXX_NOEXCEPT { return *this; } 00686 }; 00687 00688 template<typename _Key, typename _Tp, 00689 typename _Compare, typename _Allocator> 00690 inline bool 00691 operator==(const map<_Key, _Tp, _Compare, _Allocator>& __lhs, 00692 const map<_Key, _Tp, _Compare, _Allocator>& __rhs) 00693 { return __lhs._M_base() == __rhs._M_base(); } 00694 00695 template<typename _Key, typename _Tp, 00696 typename _Compare, typename _Allocator> 00697 inline bool 00698 operator!=(const map<_Key, _Tp, _Compare, _Allocator>& __lhs, 00699 const map<_Key, _Tp, _Compare, _Allocator>& __rhs) 00700 { return __lhs._M_base() != __rhs._M_base(); } 00701 00702 template<typename _Key, typename _Tp, 00703 typename _Compare, typename _Allocator> 00704 inline bool 00705 operator<(const map<_Key, _Tp, _Compare, _Allocator>& __lhs, 00706 const map<_Key, _Tp, _Compare, _Allocator>& __rhs) 00707 { return __lhs._M_base() < __rhs._M_base(); } 00708 00709 template<typename _Key, typename _Tp, 00710 typename _Compare, typename _Allocator> 00711 inline bool 00712 operator<=(const map<_Key, _Tp, _Compare, _Allocator>& __lhs, 00713 const map<_Key, _Tp, _Compare, _Allocator>& __rhs) 00714 { return __lhs._M_base() <= __rhs._M_base(); } 00715 00716 template<typename _Key, typename _Tp, 00717 typename _Compare, typename _Allocator> 00718 inline bool 00719 operator>=(const map<_Key, _Tp, _Compare, _Allocator>& __lhs, 00720 const map<_Key, _Tp, _Compare, _Allocator>& __rhs) 00721 { return __lhs._M_base() >= __rhs._M_base(); } 00722 00723 template<typename _Key, typename _Tp, 00724 typename _Compare, typename _Allocator> 00725 inline bool 00726 operator>(const map<_Key, _Tp, _Compare, _Allocator>& __lhs, 00727 const map<_Key, _Tp, _Compare, _Allocator>& __rhs) 00728 { return __lhs._M_base() > __rhs._M_base(); } 00729 00730 template<typename _Key, typename _Tp, 00731 typename _Compare, typename _Allocator> 00732 inline void 00733 swap(map<_Key, _Tp, _Compare, _Allocator>& __lhs, 00734 map<_Key, _Tp, _Compare, _Allocator>& __rhs) 00735 _GLIBCXX_NOEXCEPT_IF(noexcept(__lhs.swap(__rhs))) 00736 { __lhs.swap(__rhs); } 00737 00738 } // namespace __debug 00739 } // namespace std 00740 00741 #endif