Mercurial > hg > vamp-build-and-test
comparison DEPENDENCIES/generic/include/boost/intrusive/bstree.hpp @ 101:c530137014c0
Update Boost headers (1.58.0)
author | Chris Cannam |
---|---|
date | Mon, 07 Sep 2015 11:12:49 +0100 |
parents | 2665513ce2d3 |
children |
comparison
equal
deleted
inserted
replaced
100:793467b5e61c | 101:c530137014c0 |
---|---|
1 ///////////////////////////////////////////////////////////////////////////// | 1 ///////////////////////////////////////////////////////////////////////////// |
2 // | 2 // |
3 // (C) Copyright Ion Gaztanaga 2013-2013 | 3 // (C) Copyright Ion Gaztanaga 2013-2014 |
4 // | 4 // |
5 // Distributed under the Boost Software License, Version 1.0. | 5 // Distributed under the Boost Software License, Version 1.0. |
6 // (See accompanying file LICENSE_1_0.txt or copy at | 6 // (See accompanying file LICENSE_1_0.txt or copy at |
7 // http://www.boost.org/LICENSE_1_0.txt) | 7 // http://www.boost.org/LICENSE_1_0.txt) |
8 // | 8 // |
11 ///////////////////////////////////////////////////////////////////////////// | 11 ///////////////////////////////////////////////////////////////////////////// |
12 #ifndef BOOST_INTRUSIVE_BSTREE_HPP | 12 #ifndef BOOST_INTRUSIVE_BSTREE_HPP |
13 #define BOOST_INTRUSIVE_BSTREE_HPP | 13 #define BOOST_INTRUSIVE_BSTREE_HPP |
14 | 14 |
15 #include <boost/intrusive/detail/config_begin.hpp> | 15 #include <boost/intrusive/detail/config_begin.hpp> |
16 #include <algorithm> | 16 #include <boost/intrusive/intrusive_fwd.hpp> |
17 #include <cstddef> | |
18 #include <functional> | |
19 #include <iterator> | |
20 #include <utility> | |
21 | 17 |
22 #include <boost/intrusive/detail/assert.hpp> | 18 #include <boost/intrusive/detail/assert.hpp> |
23 #include <boost/static_assert.hpp> | 19 #include <boost/static_assert.hpp> |
24 #include <boost/intrusive/intrusive_fwd.hpp> | 20 #include <boost/intrusive/intrusive_fwd.hpp> |
25 #include <boost/intrusive/set_hook.hpp> | 21 #include <boost/intrusive/bs_set_hook.hpp> |
26 #include <boost/intrusive/detail/tree_node.hpp> | 22 #include <boost/intrusive/detail/tree_node.hpp> |
23 #include <boost/intrusive/detail/tree_iterator.hpp> | |
27 #include <boost/intrusive/detail/ebo_functor_holder.hpp> | 24 #include <boost/intrusive/detail/ebo_functor_holder.hpp> |
28 #include <boost/intrusive/detail/mpl.hpp> | 25 #include <boost/intrusive/detail/mpl.hpp> |
29 #include <boost/intrusive/pointer_traits.hpp> | 26 #include <boost/intrusive/pointer_traits.hpp> |
30 #include <boost/intrusive/detail/clear_on_destructor_base.hpp> | 27 #include <boost/intrusive/detail/is_stateful_value_traits.hpp> |
31 #include <boost/intrusive/detail/function_detector.hpp> | 28 #include <boost/intrusive/detail/empty_node_checker.hpp> |
32 #include <boost/intrusive/detail/utilities.hpp> | 29 #include <boost/intrusive/detail/default_header_holder.hpp> |
33 #include <boost/intrusive/options.hpp> | 30 #include <boost/intrusive/detail/reverse_iterator.hpp> |
31 #include <boost/intrusive/detail/exception_disposer.hpp> | |
32 #include <boost/intrusive/detail/node_cloner_disposer.hpp> | |
33 #include <boost/intrusive/detail/key_nodeptr_comp.hpp> | |
34 #include <boost/intrusive/detail/simple_disposers.hpp> | |
35 #include <boost/intrusive/detail/size_holder.hpp> | |
36 #include <boost/intrusive/detail/algo_type.hpp> | |
37 #include <boost/intrusive/detail/algorithm.hpp> | |
38 | |
39 #include <boost/intrusive/detail/get_value_traits.hpp> | |
34 #include <boost/intrusive/bstree_algorithms.hpp> | 40 #include <boost/intrusive/bstree_algorithms.hpp> |
35 #include <boost/intrusive/link_mode.hpp> | 41 #include <boost/intrusive/link_mode.hpp> |
36 #include <boost/move/move.hpp> | 42 #include <boost/intrusive/parent_from_member.hpp> |
43 #include <boost/move/utility_core.hpp> | |
44 #include <boost/move/adl_move_swap.hpp> | |
45 | |
46 #include <boost/intrusive/detail/minimal_pair_header.hpp> | |
47 #include <cstddef> //size_t... | |
48 #include <boost/intrusive/detail/minimal_less_equal_header.hpp>//less, equal_to | |
49 | |
50 #if defined(BOOST_HAS_PRAGMA_ONCE) | |
51 # pragma once | |
52 #endif | |
37 | 53 |
38 namespace boost { | 54 namespace boost { |
39 namespace intrusive { | 55 namespace intrusive { |
40 | 56 |
41 /// @cond | 57 /// @cond |
42 | 58 |
59 struct default_bstree_hook_applier | |
60 { template <class T> struct apply{ typedef typename T::default_bstree_hook type; }; }; | |
61 | |
62 template<> | |
63 struct is_default_hook_tag<default_bstree_hook_applier> | |
64 { static const bool value = true; }; | |
65 | |
43 struct bstree_defaults | 66 struct bstree_defaults |
44 { | 67 { |
45 typedef detail::default_bstree_hook proto_value_traits; | 68 typedef default_bstree_hook_applier proto_value_traits; |
46 static const bool constant_time_size = true; | 69 static const bool constant_time_size = true; |
47 typedef std::size_t size_type; | 70 typedef std::size_t size_type; |
48 typedef void compare; | 71 typedef void compare; |
49 static const bool floating_point = true; //For sgtree | 72 static const bool floating_point = true; //For sgtree |
50 typedef void priority; //For treap | 73 typedef void priority; //For treap |
74 typedef void header_holder_type; | |
51 }; | 75 }; |
52 | 76 |
53 template<class ValueTraits, algo_types AlgoType> | 77 template<class ValueTraits, algo_types AlgoType, typename HeaderHolder> |
54 struct bstbase3 | 78 struct bstbase3 |
55 : public detail::get_real_value_traits<ValueTraits>::type::node_traits::node | |
56 , public ValueTraits | |
57 { | 79 { |
58 typedef ValueTraits value_traits; | 80 typedef ValueTraits value_traits; |
59 typedef typename detail::get_real_value_traits<ValueTraits>::type real_value_traits; | 81 typedef typename value_traits::node_traits node_traits; |
60 typedef typename real_value_traits::node_traits node_traits; | |
61 typedef typename node_traits::node node_type; | 82 typedef typename node_traits::node node_type; |
62 typedef typename get_algo<AlgoType, node_traits>::type node_algorithms; | 83 typedef typename get_algo<AlgoType, node_traits>::type node_algorithms; |
63 typedef typename node_traits::node_ptr node_ptr; | 84 typedef typename node_traits::node_ptr node_ptr; |
64 typedef typename node_traits::const_node_ptr const_node_ptr; | 85 typedef typename node_traits::const_node_ptr const_node_ptr; |
65 | 86 typedef tree_iterator<value_traits, false> iterator; |
66 bstbase3(const ValueTraits &vtraits) | 87 typedef tree_iterator<value_traits, true> const_iterator; |
67 : ValueTraits(vtraits) | 88 typedef boost::intrusive::reverse_iterator<iterator> reverse_iterator; |
68 {} | 89 typedef boost::intrusive::reverse_iterator<const_iterator> const_reverse_iterator; |
69 | 90 typedef BOOST_INTRUSIVE_IMPDEF(typename value_traits::pointer) pointer; |
70 static const bool external_value_traits = | 91 typedef BOOST_INTRUSIVE_IMPDEF(typename value_traits::const_pointer) const_pointer; |
71 detail::external_value_traits_bool_is_true<ValueTraits>::value; | |
72 | |
73 node_ptr header_ptr() | |
74 { return pointer_traits<node_ptr>::pointer_to(static_cast<node_type&>(*this)); } | |
75 | |
76 const_node_ptr header_ptr() const | |
77 { return pointer_traits<const_node_ptr>::pointer_to(static_cast<const node_type&>(*this)); } | |
78 | |
79 const value_traits &val_traits() const | |
80 { return *this; } | |
81 | |
82 value_traits &val_traits() | |
83 { return *this; } | |
84 | |
85 const real_value_traits &get_real_value_traits(detail::bool_<false>) const | |
86 { return *this; } | |
87 | |
88 const real_value_traits &get_real_value_traits(detail::bool_<true>) const | |
89 { return this->val_traits().get_value_traits(*this); } | |
90 | |
91 real_value_traits &get_real_value_traits(detail::bool_<false>) | |
92 { return *this; } | |
93 | |
94 real_value_traits &get_real_value_traits(detail::bool_<true>) | |
95 { return this->val_traits().get_value_traits(*this); } | |
96 | |
97 const real_value_traits &get_real_value_traits() const | |
98 { return this->get_real_value_traits(detail::bool_<external_value_traits>()); } | |
99 | |
100 real_value_traits &get_real_value_traits() | |
101 { return this->get_real_value_traits(detail::bool_<external_value_traits>()); } | |
102 | |
103 typedef typename pointer_traits<node_ptr>::template rebind_pointer<const real_value_traits>::type const_real_value_traits_ptr; | |
104 | |
105 const_real_value_traits_ptr real_value_traits_ptr() const | |
106 { return pointer_traits<const_real_value_traits_ptr>::pointer_to(this->get_real_value_traits()); } | |
107 | |
108 | |
109 typedef tree_iterator<real_value_traits, false> iterator; | |
110 typedef tree_iterator<real_value_traits, true> const_iterator; | |
111 typedef boost::intrusive::detail::reverse_iterator<iterator> reverse_iterator; | |
112 typedef boost::intrusive::detail::reverse_iterator<const_iterator> const_reverse_iterator; | |
113 typedef BOOST_INTRUSIVE_IMPDEF(typename real_value_traits::pointer) pointer; | |
114 typedef BOOST_INTRUSIVE_IMPDEF(typename real_value_traits::const_pointer) const_pointer; | |
115 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::element_type) value_type; | 92 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::element_type) value_type; |
116 typedef BOOST_INTRUSIVE_IMPDEF(value_type) key_type; | 93 typedef BOOST_INTRUSIVE_IMPDEF(value_type) key_type; |
117 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::reference) reference; | 94 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::reference) reference; |
118 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::reference) const_reference; | 95 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::reference) const_reference; |
119 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::difference_type) difference_type; | 96 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::difference_type) difference_type; |
120 static const bool safemode_or_autounlink = is_safe_autounlink<real_value_traits::link_mode>::value; | 97 typedef typename detail::get_header_holder_type |
121 static const bool stateful_value_traits = detail::is_stateful_value_traits<real_value_traits>::value; | 98 < value_traits,HeaderHolder >::type header_holder_type; |
99 | |
100 static const bool safemode_or_autounlink = is_safe_autounlink<value_traits::link_mode>::value; | |
101 static const bool stateful_value_traits = detail::is_stateful_value_traits<value_traits>::value; | |
102 static const bool has_container_from_iterator = | |
103 detail::is_same< header_holder_type, detail::default_header_holder< node_traits > >::value; | |
104 | |
105 struct holder_t : public ValueTraits | |
106 { | |
107 explicit holder_t(const ValueTraits &vtraits) | |
108 : ValueTraits(vtraits) | |
109 {} | |
110 header_holder_type root; | |
111 } holder; | |
112 | |
113 static bstbase3 &get_tree_base_from_end_iterator(const const_iterator &end_iterator) | |
114 { | |
115 BOOST_STATIC_ASSERT(has_container_from_iterator); | |
116 node_ptr p = end_iterator.pointed_node(); | |
117 header_holder_type* h = header_holder_type::get_holder(p); | |
118 holder_t *holder = get_parent_from_member<holder_t, header_holder_type>(h, &holder_t::root); | |
119 bstbase3 *base = get_parent_from_member<bstbase3, holder_t> (holder, &bstbase3::holder); | |
120 return *base; | |
121 } | |
122 | |
123 bstbase3(const ValueTraits &vtraits) | |
124 : holder(vtraits) | |
125 { | |
126 node_algorithms::init_header(this->header_ptr()); | |
127 } | |
128 | |
129 node_ptr header_ptr() | |
130 { return holder.root.get_node(); } | |
131 | |
132 const_node_ptr header_ptr() const | |
133 { return holder.root.get_node(); } | |
134 | |
135 const value_traits &get_value_traits() const | |
136 { return this->holder; } | |
137 | |
138 value_traits &get_value_traits() | |
139 { return this->holder; } | |
140 | |
141 typedef typename boost::intrusive::value_traits_pointers | |
142 <ValueTraits>::const_value_traits_ptr const_value_traits_ptr; | |
143 | |
144 const_value_traits_ptr priv_value_traits_ptr() const | |
145 { return pointer_traits<const_value_traits_ptr>::pointer_to(this->get_value_traits()); } | |
122 | 146 |
123 iterator begin() | 147 iterator begin() |
124 { return iterator (node_traits::get_left(this->header_ptr()), this->real_value_traits_ptr()); } | 148 { return iterator(node_algorithms::begin_node(this->header_ptr()), this->priv_value_traits_ptr()); } |
125 | 149 |
126 const_iterator begin() const | 150 const_iterator begin() const |
127 { return cbegin(); } | 151 { return cbegin(); } |
128 | 152 |
129 const_iterator cbegin() const | 153 const_iterator cbegin() const |
130 { return const_iterator (node_traits::get_left(this->header_ptr()), this->real_value_traits_ptr()); } | 154 { return const_iterator(node_algorithms::begin_node(this->header_ptr()), this->priv_value_traits_ptr()); } |
131 | 155 |
132 iterator end() | 156 iterator end() |
133 { return iterator (this->header_ptr(), this->real_value_traits_ptr()); } | 157 { return iterator(node_algorithms::end_node(this->header_ptr()), this->priv_value_traits_ptr()); } |
134 | 158 |
135 const_iterator end() const | 159 const_iterator end() const |
136 { return cend(); } | 160 { return cend(); } |
137 | 161 |
138 const_iterator cend() const | 162 const_iterator cend() const |
139 { return const_iterator (detail::uncast(this->header_ptr()), this->real_value_traits_ptr()); } | 163 { return const_iterator(node_algorithms::end_node(this->header_ptr()), this->priv_value_traits_ptr()); } |
164 | |
165 iterator root() | |
166 { return iterator(node_algorithms::root_node(this->header_ptr()), this->priv_value_traits_ptr()); } | |
167 | |
168 const_iterator root() const | |
169 { return croot(); } | |
170 | |
171 const_iterator croot() const | |
172 { return const_iterator(node_algorithms::root_node(this->header_ptr()), this->priv_value_traits_ptr()); } | |
140 | 173 |
141 reverse_iterator rbegin() | 174 reverse_iterator rbegin() |
142 { return reverse_iterator(end()); } | 175 { return reverse_iterator(end()); } |
143 | 176 |
144 const_reverse_iterator rbegin() const | 177 const_reverse_iterator rbegin() const |
156 const_reverse_iterator crend() const | 189 const_reverse_iterator crend() const |
157 { return const_reverse_iterator(begin()); } | 190 { return const_reverse_iterator(begin()); } |
158 | 191 |
159 void replace_node(iterator replace_this, reference with_this) | 192 void replace_node(iterator replace_this, reference with_this) |
160 { | 193 { |
161 node_algorithms::replace_node( get_real_value_traits().to_node_ptr(*replace_this) | 194 node_algorithms::replace_node( get_value_traits().to_node_ptr(*replace_this) |
162 , this->header_ptr() | 195 , this->header_ptr() |
163 , get_real_value_traits().to_node_ptr(with_this)); | 196 , get_value_traits().to_node_ptr(with_this)); |
164 if(safemode_or_autounlink) | 197 if(safemode_or_autounlink) |
165 node_algorithms::init(replace_this.pointed_node()); | 198 node_algorithms::init(replace_this.pointed_node()); |
166 } | 199 } |
167 | 200 |
168 void rebalance() | 201 void rebalance() |
169 { node_algorithms::rebalance(this->header_ptr()); } | 202 { node_algorithms::rebalance(this->header_ptr()); } |
170 | 203 |
171 iterator rebalance_subtree(iterator root) | 204 iterator rebalance_subtree(iterator root) |
172 { return iterator(node_algorithms::rebalance_subtree(root.pointed_node()), this->real_value_traits_ptr()); } | 205 { return iterator(node_algorithms::rebalance_subtree(root.pointed_node()), this->priv_value_traits_ptr()); } |
173 | 206 |
174 static iterator s_iterator_to(reference value) | 207 static iterator s_iterator_to(reference value) |
175 { | 208 { |
176 BOOST_STATIC_ASSERT((!stateful_value_traits)); | 209 BOOST_STATIC_ASSERT((!stateful_value_traits)); |
177 return iterator (value_traits::to_node_ptr(value), const_real_value_traits_ptr()); | 210 return iterator (value_traits::to_node_ptr(value), const_value_traits_ptr()); |
178 } | 211 } |
179 | 212 |
180 static const_iterator s_iterator_to(const_reference value) | 213 static const_iterator s_iterator_to(const_reference value) |
181 { | 214 { |
182 BOOST_STATIC_ASSERT((!stateful_value_traits)); | 215 BOOST_STATIC_ASSERT((!stateful_value_traits)); |
183 return const_iterator (value_traits::to_node_ptr(const_cast<reference> (value)), const_real_value_traits_ptr()); | 216 return const_iterator (value_traits::to_node_ptr(*pointer_traits<pointer>::const_cast_from(pointer_traits<const_pointer>::pointer_to(value))), const_value_traits_ptr()); |
184 } | 217 } |
185 | 218 |
186 iterator iterator_to(reference value) | 219 iterator iterator_to(reference value) |
187 { return iterator (value_traits::to_node_ptr(value), this->real_value_traits_ptr()); } | 220 { return iterator (this->get_value_traits().to_node_ptr(value), this->priv_value_traits_ptr()); } |
188 | 221 |
189 const_iterator iterator_to(const_reference value) const | 222 const_iterator iterator_to(const_reference value) const |
190 { return const_iterator (value_traits::to_node_ptr(const_cast<reference> (value)), this->real_value_traits_ptr()); } | 223 { return const_iterator (this->get_value_traits().to_node_ptr(*pointer_traits<pointer>::const_cast_from(pointer_traits<const_pointer>::pointer_to(value))), this->priv_value_traits_ptr()); } |
191 | 224 |
192 static void init_node(reference value) | 225 static void init_node(reference value) |
193 { node_algorithms::init(value_traits::to_node_ptr(value)); } | 226 { node_algorithms::init(value_traits::to_node_ptr(value)); } |
194 | 227 |
195 }; | 228 }; |
196 | 229 |
197 template<class ValueTraits, class VoidOrKeyComp, algo_types AlgoType> | 230 template<class Less, class T> |
231 struct get_compare | |
232 { | |
233 typedef Less type; | |
234 }; | |
235 | |
236 template<class T> | |
237 struct get_compare<void, T> | |
238 { | |
239 typedef ::std::less<T> type; | |
240 }; | |
241 | |
242 template<class ValueTraits, class VoidOrKeyComp, algo_types AlgoType, typename HeaderHolder> | |
198 struct bstbase2 | 243 struct bstbase2 |
199 : public bstbase3<ValueTraits, AlgoType> | 244 //Put the (possibly empty) functor in the first position to get EBO in MSVC |
200 , public detail::ebo_functor_holder<typename get_less< VoidOrKeyComp | 245 //Use public inheritance to avoid MSVC bugs with closures |
201 , typename detail::get_real_value_traits<ValueTraits>::type::value_type | 246 : public detail::ebo_functor_holder<typename get_compare< VoidOrKeyComp |
247 , typename ValueTraits::value_type | |
202 >::type> | 248 >::type> |
249 , public bstbase3<ValueTraits, AlgoType, HeaderHolder> | |
203 { | 250 { |
204 typedef bstbase3<ValueTraits, AlgoType> treeheader_t; | 251 typedef bstbase3<ValueTraits, AlgoType, HeaderHolder> treeheader_t; |
205 typedef typename treeheader_t::real_value_traits real_value_traits; | 252 typedef typename treeheader_t::value_traits value_traits; |
206 typedef typename treeheader_t::node_algorithms node_algorithms; | 253 typedef typename treeheader_t::node_algorithms node_algorithms; |
207 typedef typename get_less | 254 typedef typename get_compare |
208 < VoidOrKeyComp, typename real_value_traits::value_type>::type value_compare; | 255 < VoidOrKeyComp, typename value_traits::value_type>::type value_compare; |
209 typedef BOOST_INTRUSIVE_IMPDEF(value_compare) key_compare; | 256 typedef BOOST_INTRUSIVE_IMPDEF(value_compare) key_compare; |
210 typedef typename treeheader_t::iterator iterator; | 257 typedef typename treeheader_t::iterator iterator; |
211 typedef typename treeheader_t::const_iterator const_iterator; | 258 typedef typename treeheader_t::const_iterator const_iterator; |
212 typedef typename treeheader_t::node_ptr node_ptr; | 259 typedef typename treeheader_t::node_ptr node_ptr; |
213 typedef typename treeheader_t::const_node_ptr const_node_ptr; | 260 typedef typename treeheader_t::const_node_ptr const_node_ptr; |
214 | 261 |
215 bstbase2(const value_compare &comp, const ValueTraits &vtraits) | 262 bstbase2(const value_compare &comp, const ValueTraits &vtraits) |
216 : treeheader_t(vtraits), detail::ebo_functor_holder<value_compare>(comp) | 263 : detail::ebo_functor_holder<value_compare>(comp), treeheader_t(vtraits) |
217 {} | 264 {} |
218 | 265 |
219 const value_compare &comp() const | 266 const value_compare &comp() const |
220 { return this->get(); } | 267 { return this->get(); } |
221 | 268 |
222 value_compare &comp() | 269 value_compare &comp() |
223 { return this->get(); } | 270 { return this->get(); } |
224 | 271 |
225 typedef BOOST_INTRUSIVE_IMPDEF(typename real_value_traits::pointer) pointer; | 272 typedef BOOST_INTRUSIVE_IMPDEF(typename value_traits::pointer) pointer; |
226 typedef BOOST_INTRUSIVE_IMPDEF(typename real_value_traits::const_pointer) const_pointer; | 273 typedef BOOST_INTRUSIVE_IMPDEF(typename value_traits::const_pointer) const_pointer; |
227 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::element_type) value_type; | 274 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::element_type) value_type; |
228 typedef BOOST_INTRUSIVE_IMPDEF(value_type) key_type; | 275 typedef BOOST_INTRUSIVE_IMPDEF(value_type) key_type; |
229 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::reference) reference; | 276 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::reference) reference; |
230 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::reference) const_reference; | 277 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::reference) const_reference; |
231 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::difference_type) difference_type; | 278 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::difference_type) difference_type; |
235 { return this->comp(); } | 282 { return this->comp(); } |
236 | 283 |
237 key_compare key_comp() const | 284 key_compare key_comp() const |
238 { return this->comp(); } | 285 { return this->comp(); } |
239 | 286 |
287 //lower_bound | |
240 iterator lower_bound(const_reference value) | 288 iterator lower_bound(const_reference value) |
241 { return this->lower_bound(value, this->comp()); } | 289 { return this->lower_bound(value, this->comp()); } |
242 | 290 |
243 const_iterator lower_bound(const_reference value) const | 291 const_iterator lower_bound(const_reference value) const |
244 { return this->lower_bound(value, this->comp()); } | 292 { return this->lower_bound(value, this->comp()); } |
245 | 293 |
246 template<class KeyType, class KeyValueCompare> | 294 template<class KeyType, class KeyValueCompare> |
247 iterator lower_bound(const KeyType &key, KeyValueCompare comp) | 295 iterator lower_bound(const KeyType &key, KeyValueCompare comp) |
248 { | 296 { |
249 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 297 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
250 key_node_comp(comp, &this->get_real_value_traits()); | 298 key_node_comp(comp, &this->get_value_traits()); |
251 return iterator(node_algorithms::lower_bound | 299 return iterator(node_algorithms::lower_bound |
252 (this->header_ptr(), key, key_node_comp), this->real_value_traits_ptr()); | 300 (this->header_ptr(), key, key_node_comp), this->priv_value_traits_ptr()); |
253 } | 301 } |
254 | 302 |
255 template<class KeyType, class KeyValueCompare> | 303 template<class KeyType, class KeyValueCompare> |
256 const_iterator lower_bound(const KeyType &key, KeyValueCompare comp) const | 304 const_iterator lower_bound(const KeyType &key, KeyValueCompare comp) const |
257 { | 305 { |
258 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 306 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
259 key_node_comp(comp, &this->get_real_value_traits()); | 307 key_node_comp(comp, &this->get_value_traits()); |
260 return const_iterator(node_algorithms::lower_bound | 308 return const_iterator(node_algorithms::lower_bound |
261 (this->header_ptr(), key, key_node_comp), this->real_value_traits_ptr()); | 309 (this->header_ptr(), key, key_node_comp), this->priv_value_traits_ptr()); |
262 } | 310 } |
263 | 311 |
312 //upper_bound | |
264 iterator upper_bound(const_reference value) | 313 iterator upper_bound(const_reference value) |
265 { return this->upper_bound(value, this->comp()); } | 314 { return this->upper_bound(value, this->comp()); } |
266 | 315 |
267 template<class KeyType, class KeyValueCompare> | 316 template<class KeyType, class KeyValueCompare> |
268 iterator upper_bound(const KeyType &key, KeyValueCompare comp) | 317 iterator upper_bound(const KeyType &key, KeyValueCompare comp) |
269 { | 318 { |
270 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 319 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
271 key_node_comp(comp, &this->get_real_value_traits()); | 320 key_node_comp(comp, &this->get_value_traits()); |
272 return iterator(node_algorithms::upper_bound | 321 return iterator(node_algorithms::upper_bound |
273 (this->header_ptr(), key, key_node_comp), this->real_value_traits_ptr()); | 322 (this->header_ptr(), key, key_node_comp), this->priv_value_traits_ptr()); |
274 } | 323 } |
275 | 324 |
276 const_iterator upper_bound(const_reference value) const | 325 const_iterator upper_bound(const_reference value) const |
277 { return this->upper_bound(value, this->comp()); } | 326 { return this->upper_bound(value, this->comp()); } |
278 | 327 |
279 template<class KeyType, class KeyValueCompare> | 328 template<class KeyType, class KeyValueCompare> |
280 const_iterator upper_bound(const KeyType &key, KeyValueCompare comp) const | 329 const_iterator upper_bound(const KeyType &key, KeyValueCompare comp) const |
281 { | 330 { |
282 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 331 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
283 key_node_comp(comp, &this->get_real_value_traits()); | 332 key_node_comp(comp, &this->get_value_traits()); |
284 return const_iterator(node_algorithms::upper_bound | 333 return const_iterator(node_algorithms::upper_bound |
285 (this->header_ptr(), key, key_node_comp), this->real_value_traits_ptr()); | 334 (this->header_ptr(), key, key_node_comp), this->priv_value_traits_ptr()); |
286 } | 335 } |
287 | 336 |
337 //find | |
288 iterator find(const_reference value) | 338 iterator find(const_reference value) |
289 { return this->find(value, this->comp()); } | 339 { return this->find(value, this->comp()); } |
290 | 340 |
291 template<class KeyType, class KeyValueCompare> | 341 template<class KeyType, class KeyValueCompare> |
292 iterator find(const KeyType &key, KeyValueCompare comp) | 342 iterator find(const KeyType &key, KeyValueCompare comp) |
293 { | 343 { |
294 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 344 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
295 key_node_comp(comp, &this->get_real_value_traits()); | 345 key_node_comp(comp, &this->get_value_traits()); |
296 return iterator | 346 return iterator |
297 (node_algorithms::find(this->header_ptr(), key, key_node_comp), this->real_value_traits_ptr()); | 347 (node_algorithms::find(this->header_ptr(), key, key_node_comp), this->priv_value_traits_ptr()); |
298 } | 348 } |
299 | 349 |
300 const_iterator find(const_reference value) const | 350 const_iterator find(const_reference value) const |
301 { return this->find(value, this->comp()); } | 351 { return this->find(value, this->comp()); } |
302 | 352 |
303 template<class KeyType, class KeyValueCompare> | 353 template<class KeyType, class KeyValueCompare> |
304 const_iterator find(const KeyType &key, KeyValueCompare comp) const | 354 const_iterator find(const KeyType &key, KeyValueCompare comp) const |
305 { | 355 { |
306 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 356 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
307 key_node_comp(comp, &this->get_real_value_traits()); | 357 key_node_comp(comp, &this->get_value_traits()); |
308 return const_iterator | 358 return const_iterator |
309 (node_algorithms::find(this->header_ptr(), key, key_node_comp), this->real_value_traits_ptr()); | 359 (node_algorithms::find(this->header_ptr(), key, key_node_comp), this->priv_value_traits_ptr()); |
310 } | 360 } |
311 | 361 |
362 //equal_range | |
312 std::pair<iterator,iterator> equal_range(const_reference value) | 363 std::pair<iterator,iterator> equal_range(const_reference value) |
313 { return this->equal_range(value, this->comp()); } | 364 { return this->equal_range(value, this->comp()); } |
314 | 365 |
315 template<class KeyType, class KeyValueCompare> | 366 template<class KeyType, class KeyValueCompare> |
316 std::pair<iterator,iterator> equal_range(const KeyType &key, KeyValueCompare comp) | 367 std::pair<iterator,iterator> equal_range(const KeyType &key, KeyValueCompare comp) |
317 { | 368 { |
318 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 369 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
319 key_node_comp(comp, &this->get_real_value_traits()); | 370 key_node_comp(comp, &this->get_value_traits()); |
320 std::pair<node_ptr, node_ptr> ret | 371 std::pair<node_ptr, node_ptr> ret |
321 (node_algorithms::equal_range(this->header_ptr(), key, key_node_comp)); | 372 (node_algorithms::equal_range(this->header_ptr(), key, key_node_comp)); |
322 return std::pair<iterator, iterator>( iterator(ret.first, this->real_value_traits_ptr()) | 373 return std::pair<iterator, iterator>( iterator(ret.first, this->priv_value_traits_ptr()) |
323 , iterator(ret.second, this->real_value_traits_ptr())); | 374 , iterator(ret.second, this->priv_value_traits_ptr())); |
324 } | 375 } |
325 | 376 |
326 std::pair<const_iterator, const_iterator> | 377 std::pair<const_iterator, const_iterator> |
327 equal_range(const_reference value) const | 378 equal_range(const_reference value) const |
328 { return this->equal_range(value, this->comp()); } | 379 { return this->equal_range(value, this->comp()); } |
329 | 380 |
330 template<class KeyType, class KeyValueCompare> | 381 template<class KeyType, class KeyValueCompare> |
331 std::pair<const_iterator, const_iterator> | 382 std::pair<const_iterator, const_iterator> |
332 equal_range(const KeyType &key, KeyValueCompare comp) const | 383 equal_range(const KeyType &key, KeyValueCompare comp) const |
333 { | 384 { |
334 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 385 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
335 key_node_comp(comp, &this->get_real_value_traits()); | 386 key_node_comp(comp, &this->get_value_traits()); |
336 std::pair<node_ptr, node_ptr> ret | 387 std::pair<node_ptr, node_ptr> ret |
337 (node_algorithms::equal_range(this->header_ptr(), key, key_node_comp)); | 388 (node_algorithms::equal_range(this->header_ptr(), key, key_node_comp)); |
338 return std::pair<const_iterator, const_iterator>( const_iterator(ret.first, this->real_value_traits_ptr()) | 389 return std::pair<const_iterator, const_iterator>( const_iterator(ret.first, this->priv_value_traits_ptr()) |
339 , const_iterator(ret.second, this->real_value_traits_ptr())); | 390 , const_iterator(ret.second, this->priv_value_traits_ptr())); |
340 } | 391 } |
341 | 392 |
393 //lower_bound_range | |
394 std::pair<iterator,iterator> lower_bound_range(const_reference value) | |
395 { return this->lower_bound_range(value, this->comp()); } | |
396 | |
397 template<class KeyType, class KeyValueCompare> | |
398 std::pair<iterator,iterator> lower_bound_range(const KeyType &key, KeyValueCompare comp) | |
399 { | |
400 detail::key_nodeptr_comp<KeyValueCompare, value_traits> | |
401 key_node_comp(comp, &this->get_value_traits()); | |
402 std::pair<node_ptr, node_ptr> ret | |
403 (node_algorithms::lower_bound_range(this->header_ptr(), key, key_node_comp)); | |
404 return std::pair<iterator, iterator>( iterator(ret.first, this->priv_value_traits_ptr()) | |
405 , iterator(ret.second, this->priv_value_traits_ptr())); | |
406 } | |
407 | |
408 std::pair<const_iterator, const_iterator> | |
409 lower_bound_range(const_reference value) const | |
410 { return this->lower_bound_range(value, this->comp()); } | |
411 | |
412 template<class KeyType, class KeyValueCompare> | |
413 std::pair<const_iterator, const_iterator> | |
414 lower_bound_range(const KeyType &key, KeyValueCompare comp) const | |
415 { | |
416 detail::key_nodeptr_comp<KeyValueCompare, value_traits> | |
417 key_node_comp(comp, &this->get_value_traits()); | |
418 std::pair<node_ptr, node_ptr> ret | |
419 (node_algorithms::lower_bound_range(this->header_ptr(), key, key_node_comp)); | |
420 return std::pair<const_iterator, const_iterator>( const_iterator(ret.first, this->priv_value_traits_ptr()) | |
421 , const_iterator(ret.second, this->priv_value_traits_ptr())); | |
422 } | |
423 | |
424 //bounded_range | |
342 std::pair<iterator,iterator> bounded_range | 425 std::pair<iterator,iterator> bounded_range |
343 (const_reference lower_value, const_reference upper_value, bool left_closed, bool right_closed) | 426 (const_reference lower_value, const_reference upper_value, bool left_closed, bool right_closed) |
344 { return this->bounded_range(lower_value, upper_value, this->comp(), left_closed, right_closed); } | 427 { return this->bounded_range(lower_value, upper_value, this->comp(), left_closed, right_closed); } |
345 | 428 |
346 template<class KeyType, class KeyValueCompare> | 429 template<class KeyType, class KeyValueCompare> |
347 std::pair<iterator,iterator> bounded_range | 430 std::pair<iterator,iterator> bounded_range |
348 (const KeyType &lower_key, const KeyType &upper_key, KeyValueCompare comp, bool left_closed, bool right_closed) | 431 (const KeyType &lower_key, const KeyType &upper_key, KeyValueCompare comp, bool left_closed, bool right_closed) |
349 { | 432 { |
350 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 433 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
351 key_node_comp(comp, &this->get_real_value_traits()); | 434 key_node_comp(comp, &this->get_value_traits()); |
352 std::pair<node_ptr, node_ptr> ret | 435 std::pair<node_ptr, node_ptr> ret |
353 (node_algorithms::bounded_range | 436 (node_algorithms::bounded_range |
354 (this->header_ptr(), lower_key, upper_key, key_node_comp, left_closed, right_closed)); | 437 (this->header_ptr(), lower_key, upper_key, key_node_comp, left_closed, right_closed)); |
355 return std::pair<iterator, iterator>( iterator(ret.first, this->real_value_traits_ptr()) | 438 return std::pair<iterator, iterator>( iterator(ret.first, this->priv_value_traits_ptr()) |
356 , iterator(ret.second, this->real_value_traits_ptr())); | 439 , iterator(ret.second, this->priv_value_traits_ptr())); |
357 } | 440 } |
358 | 441 |
359 std::pair<const_iterator,const_iterator> bounded_range | 442 std::pair<const_iterator,const_iterator> bounded_range |
360 (const_reference lower_value, const_reference upper_value, bool left_closed, bool right_closed) const | 443 (const_reference lower_value, const_reference upper_value, bool left_closed, bool right_closed) const |
361 { return this->bounded_range(lower_value, upper_value, this->comp(), left_closed, right_closed); } | 444 { return this->bounded_range(lower_value, upper_value, this->comp(), left_closed, right_closed); } |
362 | 445 |
363 template<class KeyType, class KeyValueCompare> | 446 template<class KeyType, class KeyValueCompare> |
364 std::pair<const_iterator,const_iterator> bounded_range | 447 std::pair<const_iterator,const_iterator> bounded_range |
365 (const KeyType &lower_key, const KeyType &upper_key, KeyValueCompare comp, bool left_closed, bool right_closed) const | 448 (const KeyType &lower_key, const KeyType &upper_key, KeyValueCompare comp, bool left_closed, bool right_closed) const |
366 { | 449 { |
367 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 450 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
368 key_node_comp(comp, &this->get_real_value_traits()); | 451 key_node_comp(comp, &this->get_value_traits()); |
369 std::pair<node_ptr, node_ptr> ret | 452 std::pair<node_ptr, node_ptr> ret |
370 (node_algorithms::bounded_range | 453 (node_algorithms::bounded_range |
371 (this->header_ptr(), lower_key, upper_key, key_node_comp, left_closed, right_closed)); | 454 (this->header_ptr(), lower_key, upper_key, key_node_comp, left_closed, right_closed)); |
372 return std::pair<const_iterator, const_iterator>( const_iterator(ret.first, this->real_value_traits_ptr()) | 455 return std::pair<const_iterator, const_iterator>( const_iterator(ret.first, this->priv_value_traits_ptr()) |
373 , const_iterator(ret.second, this->real_value_traits_ptr())); | 456 , const_iterator(ret.second, this->priv_value_traits_ptr())); |
374 } | 457 } |
375 | 458 |
459 //insert_unique_check | |
376 template<class KeyType, class KeyValueCompare> | 460 template<class KeyType, class KeyValueCompare> |
377 std::pair<iterator, bool> insert_unique_check | 461 std::pair<iterator, bool> insert_unique_check |
378 (const KeyType &key, KeyValueCompare key_value_comp, insert_commit_data &commit_data) | 462 (const KeyType &key, KeyValueCompare key_value_comp, insert_commit_data &commit_data) |
379 { | 463 { |
380 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 464 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
381 ocomp(key_value_comp, &this->get_real_value_traits()); | 465 ocomp(key_value_comp, &this->get_value_traits()); |
382 std::pair<node_ptr, bool> ret = | 466 std::pair<node_ptr, bool> ret = |
383 (node_algorithms::insert_unique_check | 467 (node_algorithms::insert_unique_check |
384 (this->header_ptr(), key, ocomp, commit_data)); | 468 (this->header_ptr(), key, ocomp, commit_data)); |
385 return std::pair<iterator, bool>(iterator(ret.first, this->real_value_traits_ptr()), ret.second); | 469 return std::pair<iterator, bool>(iterator(ret.first, this->priv_value_traits_ptr()), ret.second); |
386 } | 470 } |
387 | 471 |
388 template<class KeyType, class KeyValueCompare> | 472 template<class KeyType, class KeyValueCompare> |
389 std::pair<iterator, bool> insert_unique_check | 473 std::pair<iterator, bool> insert_unique_check |
390 (const_iterator hint, const KeyType &key | 474 (const_iterator hint, const KeyType &key |
391 ,KeyValueCompare key_value_comp, insert_commit_data &commit_data) | 475 ,KeyValueCompare key_value_comp, insert_commit_data &commit_data) |
392 { | 476 { |
393 detail::key_nodeptr_comp<KeyValueCompare, real_value_traits> | 477 detail::key_nodeptr_comp<KeyValueCompare, value_traits> |
394 ocomp(key_value_comp, &this->get_real_value_traits()); | 478 ocomp(key_value_comp, &this->get_value_traits()); |
395 std::pair<node_ptr, bool> ret = | 479 std::pair<node_ptr, bool> ret = |
396 (node_algorithms::insert_unique_check | 480 (node_algorithms::insert_unique_check |
397 (this->header_ptr(), hint.pointed_node(), key, ocomp, commit_data)); | 481 (this->header_ptr(), hint.pointed_node(), key, ocomp, commit_data)); |
398 return std::pair<iterator, bool>(iterator(ret.first, this->real_value_traits_ptr()), ret.second); | 482 return std::pair<iterator, bool>(iterator(ret.first, this->priv_value_traits_ptr()), ret.second); |
399 } | 483 } |
400 }; | 484 }; |
401 | 485 |
402 template<class ValueTraits, class VoidOrKeyComp, bool ConstantTimeSize, class SizeType, algo_types AlgoType> | 486 //Due to MSVC's EBO implementation, to save space and maintain the ABI, we must put the non-empty size member |
487 //in the first position, but if size is not going to be stored then we'll use an specialization | |
488 //that doesn't inherit from size_holder | |
489 template<class ValueTraits, class VoidOrKeyComp, bool ConstantTimeSize, class SizeType, algo_types AlgoType, typename HeaderHolder> | |
490 struct bstbase_hack | |
491 : public detail::size_holder<ConstantTimeSize, SizeType> | |
492 , public bstbase2 < ValueTraits, VoidOrKeyComp, AlgoType, HeaderHolder> | |
493 { | |
494 typedef bstbase2< ValueTraits, VoidOrKeyComp, AlgoType, HeaderHolder> base_type; | |
495 typedef typename base_type::value_compare value_compare; | |
496 typedef SizeType size_type; | |
497 typedef typename base_type::node_traits node_traits; | |
498 typedef typename get_algo | |
499 <AlgoType, node_traits>::type algo_type; | |
500 | |
501 bstbase_hack(const value_compare & comp, const ValueTraits &vtraits) | |
502 : base_type(comp, vtraits) | |
503 { | |
504 this->sz_traits().set_size(size_type(0)); | |
505 } | |
506 | |
507 typedef detail::size_holder<ConstantTimeSize, SizeType> size_traits; | |
508 | |
509 size_traits &sz_traits() | |
510 { return static_cast<size_traits &>(*this); } | |
511 | |
512 const size_traits &sz_traits() const | |
513 { return static_cast<const size_traits &>(*this); } | |
514 }; | |
515 | |
516 //Specialization for ConstantTimeSize == false | |
517 template<class ValueTraits, class VoidOrKeyComp, class SizeType, algo_types AlgoType, typename HeaderHolder> | |
518 struct bstbase_hack<ValueTraits, VoidOrKeyComp, false, SizeType, AlgoType, HeaderHolder> | |
519 : public bstbase2 < ValueTraits, VoidOrKeyComp, AlgoType, HeaderHolder> | |
520 { | |
521 typedef bstbase2< ValueTraits, VoidOrKeyComp, AlgoType, HeaderHolder> base_type; | |
522 typedef typename base_type::value_compare value_compare; | |
523 bstbase_hack(const value_compare & comp, const ValueTraits &vtraits) | |
524 : base_type(comp, vtraits) | |
525 {} | |
526 | |
527 typedef detail::size_holder<true, SizeType> size_traits; | |
528 | |
529 size_traits &sz_traits() | |
530 { return s_size_traits; } | |
531 | |
532 const size_traits &sz_traits() const | |
533 { return s_size_traits; } | |
534 | |
535 static size_traits s_size_traits; | |
536 }; | |
537 | |
538 template<class ValueTraits, class VoidOrKeyComp, class SizeType, algo_types AlgoType, typename HeaderHolder> | |
539 detail::size_holder<true, SizeType> bstbase_hack<ValueTraits, VoidOrKeyComp, false, SizeType, AlgoType, HeaderHolder>::s_size_traits; | |
540 | |
541 //This class will | |
542 template<class ValueTraits, class VoidOrKeyComp, bool ConstantTimeSize, class SizeType, algo_types AlgoType, typename HeaderHolder> | |
403 struct bstbase | 543 struct bstbase |
404 : public detail::size_holder<ConstantTimeSize, SizeType> | 544 : public bstbase_hack< ValueTraits, VoidOrKeyComp, ConstantTimeSize, SizeType, AlgoType, HeaderHolder> |
405 , public bstbase2 < ValueTraits, VoidOrKeyComp, AlgoType> | |
406 { | 545 { |
407 typedef typename detail::get_real_value_traits<ValueTraits>::type real_value_traits; | 546 typedef bstbase_hack< ValueTraits, VoidOrKeyComp, ConstantTimeSize, SizeType, AlgoType, HeaderHolder> base_type; |
408 typedef bstbase2< ValueTraits, VoidOrKeyComp, AlgoType> base_type; | 547 typedef ValueTraits value_traits; |
409 typedef typename base_type::value_compare value_compare; | 548 typedef typename base_type::value_compare value_compare; |
410 typedef BOOST_INTRUSIVE_IMPDEF(value_compare) key_compare; | 549 typedef value_compare key_compare; |
411 typedef typename base_type::const_reference const_reference; | 550 typedef typename base_type::const_reference const_reference; |
412 typedef typename base_type::reference reference; | 551 typedef typename base_type::reference reference; |
413 typedef typename base_type::iterator iterator; | 552 typedef typename base_type::iterator iterator; |
414 typedef typename base_type::const_iterator const_iterator; | 553 typedef typename base_type::const_iterator const_iterator; |
415 typedef typename base_type::node_traits node_traits; | 554 typedef typename base_type::node_traits node_traits; |
416 typedef typename get_algo | 555 typedef typename get_algo |
417 <AlgoType, node_traits>::type algo_type; | 556 <AlgoType, node_traits>::type node_algorithms; |
418 typedef SizeType size_type; | 557 typedef SizeType size_type; |
419 | 558 |
420 bstbase(const value_compare & comp, const ValueTraits &vtraits) | 559 bstbase(const value_compare & comp, const ValueTraits &vtraits) |
421 : base_type(comp, vtraits) | 560 : base_type(comp, vtraits) |
422 {} | 561 {} |
423 | 562 |
424 public: | 563 //Detach all inserted nodes. This will add exception safety to bstree_impl |
425 typedef detail::size_holder<ConstantTimeSize, SizeType> size_traits; | 564 //constructors inserting elements. |
426 | 565 ~bstbase() |
427 size_traits &sz_traits() | 566 { |
428 { return *this; } | 567 if(is_safe_autounlink<value_traits::link_mode>::value){ |
429 | 568 node_algorithms::clear_and_dispose |
430 const size_traits &sz_traits() const | 569 ( this->header_ptr() |
431 { return *this; } | 570 , detail::node_disposer<detail::null_disposer, value_traits, AlgoType> |
432 | 571 (detail::null_disposer(), &this->get_value_traits())); |
433 size_type count(const_reference value) const | 572 node_algorithms::init(this->header_ptr()); |
434 { return size_type(this->count(value, this->comp())); } | |
435 | |
436 template<class KeyType, class KeyValueCompare> | |
437 size_type count(const KeyType &key, KeyValueCompare comp) const | |
438 { | |
439 std::pair<const_iterator, const_iterator> ret = this->equal_range(key, comp); | |
440 return size_type(std::distance(ret.first, ret.second)); | |
441 } | |
442 | |
443 bool empty() const | |
444 { | |
445 if(ConstantTimeSize){ | |
446 return !this->sz_traits().get_size(); | |
447 } | |
448 else{ | |
449 return algo_type::unique(this->header_ptr()); | |
450 } | 573 } |
451 } | 574 } |
452 }; | 575 }; |
453 | 576 |
454 | 577 |
470 //! \c constant_time_size<>, \c size_type<> and | 593 //! \c constant_time_size<>, \c size_type<> and |
471 //! \c compare<>. | 594 //! \c compare<>. |
472 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 595 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
473 template<class T, class ...Options> | 596 template<class T, class ...Options> |
474 #else | 597 #else |
475 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType> | 598 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType, typename HeaderHolder> |
476 #endif | 599 #endif |
477 class bstree_impl | 600 class bstree_impl |
478 : public bstbase<ValueTraits, VoidKeyComp, ConstantTimeSize, SizeType, AlgoType> | 601 : public bstbase<ValueTraits, VoidKeyComp, ConstantTimeSize, SizeType, AlgoType, HeaderHolder> |
479 , private detail::clear_on_destructor_base | |
480 < bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> | |
481 , is_safe_autounlink<detail::get_real_value_traits<ValueTraits>::type::link_mode>::value | |
482 > | |
483 { | 602 { |
484 template<class C, bool> friend class detail::clear_on_destructor_base; | |
485 public: | 603 public: |
486 typedef ValueTraits value_traits; | |
487 /// @cond | 604 /// @cond |
488 static const bool external_value_traits = | 605 typedef bstbase<ValueTraits, VoidKeyComp, ConstantTimeSize, SizeType, AlgoType, HeaderHolder> data_type; |
489 detail::external_value_traits_bool_is_true<value_traits>::value; | 606 typedef tree_iterator<ValueTraits, false> iterator_type; |
490 typedef typename detail::get_real_value_traits<ValueTraits>::type real_value_traits; | 607 typedef tree_iterator<ValueTraits, true> const_iterator_type; |
491 typedef bstbase<value_traits, VoidKeyComp, ConstantTimeSize, SizeType, AlgoType> data_type; | |
492 typedef tree_iterator<real_value_traits, false> iterator_type; | |
493 typedef tree_iterator<real_value_traits, true> const_iterator_type; | |
494 /// @endcond | 608 /// @endcond |
495 | 609 |
496 typedef BOOST_INTRUSIVE_IMPDEF(typename real_value_traits::pointer) pointer; | 610 typedef BOOST_INTRUSIVE_IMPDEF(ValueTraits) value_traits; |
497 typedef BOOST_INTRUSIVE_IMPDEF(typename real_value_traits::const_pointer) const_pointer; | 611 typedef BOOST_INTRUSIVE_IMPDEF(typename value_traits::pointer) pointer; |
612 typedef BOOST_INTRUSIVE_IMPDEF(typename value_traits::const_pointer) const_pointer; | |
498 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::element_type) value_type; | 613 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::element_type) value_type; |
499 typedef BOOST_INTRUSIVE_IMPDEF(value_type) key_type; | 614 typedef BOOST_INTRUSIVE_IMPDEF(value_type) key_type; |
500 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::reference) reference; | 615 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<pointer>::reference) reference; |
501 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::reference) const_reference; | 616 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::reference) const_reference; |
502 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::difference_type) difference_type; | 617 typedef BOOST_INTRUSIVE_IMPDEF(typename pointer_traits<const_pointer>::difference_type) difference_type; |
503 typedef BOOST_INTRUSIVE_IMPDEF(SizeType) size_type; | 618 typedef BOOST_INTRUSIVE_IMPDEF(SizeType) size_type; |
504 typedef BOOST_INTRUSIVE_IMPDEF(typename data_type::value_compare) value_compare; | 619 typedef BOOST_INTRUSIVE_IMPDEF(typename data_type::value_compare) value_compare; |
505 typedef BOOST_INTRUSIVE_IMPDEF(value_compare) key_compare; | 620 typedef BOOST_INTRUSIVE_IMPDEF(value_compare) key_compare; |
506 typedef BOOST_INTRUSIVE_IMPDEF(iterator_type) iterator; | 621 typedef BOOST_INTRUSIVE_IMPDEF(iterator_type) iterator; |
507 typedef BOOST_INTRUSIVE_IMPDEF(const_iterator_type) const_iterator; | 622 typedef BOOST_INTRUSIVE_IMPDEF(const_iterator_type) const_iterator; |
508 typedef BOOST_INTRUSIVE_IMPDEF(boost::intrusive::detail::reverse_iterator<iterator>) reverse_iterator; | 623 typedef BOOST_INTRUSIVE_IMPDEF(boost::intrusive::reverse_iterator<iterator>) reverse_iterator; |
509 typedef BOOST_INTRUSIVE_IMPDEF(boost::intrusive::detail::reverse_iterator<const_iterator>) const_reverse_iterator; | 624 typedef BOOST_INTRUSIVE_IMPDEF(boost::intrusive::reverse_iterator<const_iterator>) const_reverse_iterator; |
510 typedef BOOST_INTRUSIVE_IMPDEF(typename real_value_traits::node_traits) node_traits; | 625 typedef BOOST_INTRUSIVE_IMPDEF(typename value_traits::node_traits) node_traits; |
511 typedef BOOST_INTRUSIVE_IMPDEF(typename node_traits::node) node; | 626 typedef BOOST_INTRUSIVE_IMPDEF(typename node_traits::node) node; |
512 typedef BOOST_INTRUSIVE_IMPDEF(typename node_traits::node_ptr) node_ptr; | 627 typedef BOOST_INTRUSIVE_IMPDEF(typename node_traits::node_ptr) node_ptr; |
513 typedef BOOST_INTRUSIVE_IMPDEF(typename node_traits::const_node_ptr) const_node_ptr; | 628 typedef BOOST_INTRUSIVE_IMPDEF(typename node_traits::const_node_ptr) const_node_ptr; |
514 /// @cond | 629 /// @cond |
515 typedef typename get_algo<AlgoType, node_traits>::type algo_type; | 630 typedef typename get_algo<AlgoType, node_traits>::type algo_type; |
516 /// @endcond | 631 /// @endcond |
517 typedef BOOST_INTRUSIVE_IMPDEF(algo_type) node_algorithms; | 632 typedef BOOST_INTRUSIVE_IMPDEF(algo_type) node_algorithms; |
518 | 633 |
519 static const bool constant_time_size = ConstantTimeSize; | 634 static const bool constant_time_size = ConstantTimeSize; |
520 static const bool stateful_value_traits = detail::is_stateful_value_traits<real_value_traits>::value; | 635 static const bool stateful_value_traits = detail::is_stateful_value_traits<value_traits>::value; |
521 /// @cond | 636 /// @cond |
522 private: | 637 private: |
523 | 638 |
524 //noncopyable | 639 //noncopyable |
525 BOOST_MOVABLE_BUT_NOT_COPYABLE(bstree_impl) | 640 BOOST_MOVABLE_BUT_NOT_COPYABLE(bstree_impl) |
526 | 641 |
527 static const bool safemode_or_autounlink = is_safe_autounlink<real_value_traits::link_mode>::value; | 642 static const bool safemode_or_autounlink = is_safe_autounlink<value_traits::link_mode>::value; |
528 | 643 |
529 //Constant-time size is incompatible with auto-unlink hooks! | 644 //Constant-time size is incompatible with auto-unlink hooks! |
530 BOOST_STATIC_ASSERT(!(constant_time_size && ((int)real_value_traits::link_mode == (int)auto_unlink))); | 645 BOOST_STATIC_ASSERT(!(constant_time_size && ((int)value_traits::link_mode == (int)auto_unlink))); |
531 | 646 |
532 | 647 |
533 protected: | 648 protected: |
534 | 649 |
535 | 650 |
543 //! | 658 //! |
544 //! <b>Complexity</b>: Constant. | 659 //! <b>Complexity</b>: Constant. |
545 //! | 660 //! |
546 //! <b>Throws</b>: If value_traits::node_traits::node | 661 //! <b>Throws</b>: If value_traits::node_traits::node |
547 //! constructor throws (this does not happen with predefined Boost.Intrusive hooks) | 662 //! constructor throws (this does not happen with predefined Boost.Intrusive hooks) |
548 //! or the copy constructorof the value_compare object throws. Basic guarantee. | 663 //! or the copy constructor of the value_compare object throws. Basic guarantee. |
549 explicit bstree_impl( const value_compare &cmp = value_compare() | 664 explicit bstree_impl( const value_compare &cmp = value_compare() |
550 , const value_traits &v_traits = value_traits()) | 665 , const value_traits &v_traits = value_traits()) |
551 : data_type(cmp, v_traits) | 666 : data_type(cmp, v_traits) |
552 { | 667 {} |
553 node_algorithms::init_header(this->header_ptr()); | |
554 this->sz_traits().set_size(size_type(0)); | |
555 } | |
556 | 668 |
557 //! <b>Requires</b>: Dereferencing iterator must yield an lvalue of type value_type. | 669 //! <b>Requires</b>: Dereferencing iterator must yield an lvalue of type value_type. |
558 //! cmp must be a comparison function that induces a strict weak ordering. | 670 //! cmp must be a comparison function that induces a strict weak ordering. |
559 //! | 671 //! |
560 //! <b>Effects</b>: Constructs an empty container and inserts elements from | 672 //! <b>Effects</b>: Constructs an empty container and inserts elements from |
570 bstree_impl( bool unique, Iterator b, Iterator e | 682 bstree_impl( bool unique, Iterator b, Iterator e |
571 , const value_compare &cmp = value_compare() | 683 , const value_compare &cmp = value_compare() |
572 , const value_traits &v_traits = value_traits()) | 684 , const value_traits &v_traits = value_traits()) |
573 : data_type(cmp, v_traits) | 685 : data_type(cmp, v_traits) |
574 { | 686 { |
575 node_algorithms::init_header(this->header_ptr()); | 687 //bstbase releases elements in case of exceptions |
576 this->sz_traits().set_size(size_type(0)); | |
577 if(unique) | 688 if(unique) |
578 this->insert_unique(b, e); | 689 this->insert_unique(b, e); |
579 else | 690 else |
580 this->insert_equal(b, e); | 691 this->insert_equal(b, e); |
581 } | 692 } |
582 | 693 |
583 //! <b>Effects</b>: to-do | 694 //! <b>Effects</b>: to-do |
584 //! | 695 //! |
585 bstree_impl(BOOST_RV_REF(bstree_impl) x) | 696 bstree_impl(BOOST_RV_REF(bstree_impl) x) |
586 : data_type(::boost::move(x.comp()), ::boost::move(x.val_traits())) | 697 : data_type(::boost::move(x.comp()), ::boost::move(x.get_value_traits())) |
587 { | 698 { |
588 node_algorithms::init_header(this->header_ptr()); | |
589 this->sz_traits().set_size(size_type(0)); | |
590 this->swap(x); | 699 this->swap(x); |
591 } | 700 } |
592 | 701 |
593 //! <b>Effects</b>: to-do | 702 //! <b>Effects</b>: to-do |
594 //! | 703 //! |
706 //! <b>Throws</b>: Nothing. | 815 //! <b>Throws</b>: Nothing. |
707 //! | 816 //! |
708 //! <b>Complexity</b>: Constant. | 817 //! <b>Complexity</b>: Constant. |
709 static bstree_impl &container_from_end_iterator(iterator end_iterator) | 818 static bstree_impl &container_from_end_iterator(iterator end_iterator) |
710 { | 819 { |
711 return *static_cast<bstree_impl*> | 820 return static_cast<bstree_impl&> |
712 (boost::intrusive::detail::to_raw_pointer(end_iterator.pointed_node())); | 821 (data_type::get_tree_base_from_end_iterator(end_iterator)); |
713 } | 822 } |
714 | 823 |
715 //! <b>Precondition</b>: end_iterator must be a valid end const_iterator | 824 //! <b>Precondition</b>: end_iterator must be a valid end const_iterator |
716 //! of the container. | 825 //! of the container. |
717 //! | 826 //! |
720 //! <b>Throws</b>: Nothing. | 829 //! <b>Throws</b>: Nothing. |
721 //! | 830 //! |
722 //! <b>Complexity</b>: Constant. | 831 //! <b>Complexity</b>: Constant. |
723 static const bstree_impl &container_from_end_iterator(const_iterator end_iterator) | 832 static const bstree_impl &container_from_end_iterator(const_iterator end_iterator) |
724 { | 833 { |
725 return *static_cast<const bstree_impl*> | 834 return static_cast<bstree_impl&> |
726 (boost::intrusive::detail::to_raw_pointer(end_iterator.pointed_node())); | 835 (data_type::get_tree_base_from_end_iterator(end_iterator)); |
727 } | 836 } |
728 | 837 |
729 //! <b>Precondition</b>: it must be a valid iterator | 838 //! <b>Precondition</b>: it must be a valid iterator |
730 //! of the container. | 839 //! of the container. |
731 //! | 840 //! |
754 //! | 863 //! |
755 //! <b>Complexity</b>: Constant. | 864 //! <b>Complexity</b>: Constant. |
756 //! | 865 //! |
757 //! <b>Throws</b>: If value_compare copy-constructor throws. | 866 //! <b>Throws</b>: If value_compare copy-constructor throws. |
758 key_compare key_comp() const; | 867 key_compare key_comp() const; |
759 | 868 |
760 //! <b>Effects</b>: Returns the value_compare object used by the container. | 869 //! <b>Effects</b>: Returns the value_compare object used by the container. |
761 //! | 870 //! |
762 //! <b>Complexity</b>: Constant. | 871 //! <b>Complexity</b>: Constant. |
763 //! | 872 //! |
764 //! <b>Throws</b>: If value_compare copy-constructor throws. | 873 //! <b>Throws</b>: If value_compare copy-constructor throws. |
765 value_compare value_comp() const; | 874 value_compare value_comp() const; |
766 | 875 |
876 #endif //#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED | |
877 | |
767 //! <b>Effects</b>: Returns true if the container is empty. | 878 //! <b>Effects</b>: Returns true if the container is empty. |
768 //! | 879 //! |
769 //! <b>Complexity</b>: Constant. | 880 //! <b>Complexity</b>: Constant. |
770 //! | 881 //! |
771 //! <b>Throws</b>: Nothing. | 882 //! <b>Throws</b>: Nothing. |
772 bool empty() const; | 883 bool empty() const |
773 | 884 { |
774 #endif //#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED | 885 if(ConstantTimeSize){ |
886 return !this->data_type::sz_traits().get_size(); | |
887 } | |
888 else{ | |
889 return algo_type::unique(this->header_ptr()); | |
890 } | |
891 } | |
775 | 892 |
776 //! <b>Effects</b>: Returns the number of elements stored in the container. | 893 //! <b>Effects</b>: Returns the number of elements stored in the container. |
777 //! | 894 //! |
778 //! <b>Complexity</b>: Linear to elements contained in *this | 895 //! <b>Complexity</b>: Linear to elements contained in *this |
779 //! if constant-time size option is disabled. Constant time otherwise. | 896 //! if constant-time size option is disabled. Constant time otherwise. |
794 //! | 911 //! |
795 //! <b>Throws</b>: If the comparison functor's swap call throws. | 912 //! <b>Throws</b>: If the comparison functor's swap call throws. |
796 void swap(bstree_impl& other) | 913 void swap(bstree_impl& other) |
797 { | 914 { |
798 //This can throw | 915 //This can throw |
799 using std::swap; | 916 ::boost::adl_move_swap(this->comp(), this->comp()); |
800 swap(this->comp(), this->comp()); | |
801 //These can't throw | 917 //These can't throw |
802 node_algorithms::swap_tree(this->header_ptr(), node_ptr(other.header_ptr())); | 918 node_algorithms::swap_tree(this->header_ptr(), node_ptr(other.header_ptr())); |
803 if(constant_time_size){ | 919 if(constant_time_size){ |
804 size_type backup = this->sz_traits().get_size(); | 920 size_type backup = this->sz_traits().get_size(); |
805 this->sz_traits().set_size(other.sz_traits().get_size()); | 921 this->sz_traits().set_size(other.sz_traits().get_size()); |
827 this->clear_and_dispose(disposer); | 943 this->clear_and_dispose(disposer); |
828 if(!src.empty()){ | 944 if(!src.empty()){ |
829 detail::exception_disposer<bstree_impl, Disposer> | 945 detail::exception_disposer<bstree_impl, Disposer> |
830 rollback(*this, disposer); | 946 rollback(*this, disposer); |
831 node_algorithms::clone | 947 node_algorithms::clone |
832 (const_node_ptr(src.header_ptr()) | 948 (src.header_ptr() |
833 ,node_ptr(this->header_ptr()) | 949 ,this->header_ptr() |
834 ,detail::node_cloner <Cloner, real_value_traits, AlgoType>(cloner, &this->get_real_value_traits()) | 950 ,detail::node_cloner <Cloner, value_traits, AlgoType>(cloner, &this->get_value_traits()) |
835 ,detail::node_disposer<Disposer, real_value_traits, AlgoType>(disposer, &this->get_real_value_traits())); | 951 ,detail::node_disposer<Disposer, value_traits, AlgoType>(disposer, &this->get_value_traits())); |
836 this->sz_traits().set_size(src.sz_traits().get_size()); | 952 this->sz_traits().set_size(src.sz_traits().get_size()); |
837 this->comp() = src.comp(); | 953 this->comp() = src.comp(); |
838 rollback.release(); | 954 rollback.release(); |
839 } | 955 } |
840 } | 956 } |
841 | 957 |
958 //! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw. | |
959 //! Cloner should yield to nodes equivalent to the original nodes. | |
960 //! | |
961 //! <b>Effects</b>: Erases all the elements from *this | |
962 //! calling Disposer::operator()(pointer), clones all the | |
963 //! elements from src calling Cloner::operator()(const_reference ) | |
964 //! and inserts them on *this. Copies the predicate from the source container. | |
965 //! | |
966 //! If cloner throws, all cloned elements are unlinked and disposed | |
967 //! calling Disposer::operator()(pointer). | |
968 //! | |
969 //! <b>Complexity</b>: Linear to erased plus inserted elements. | |
970 //! | |
971 //! <b>Throws</b>: If cloner throws or predicate copy assignment throws. Basic guarantee. | |
972 //! | |
973 //! <b>Note</b>: This version can modify the source container, useful to implement | |
974 //! move semantics. | |
975 template <class Cloner, class Disposer> | |
976 void clone_from(bstree_impl &src, Cloner cloner, Disposer disposer) | |
977 { | |
978 this->clear_and_dispose(disposer); | |
979 if(!src.empty()){ | |
980 detail::exception_disposer<bstree_impl, Disposer> | |
981 rollback(*this, disposer); | |
982 node_algorithms::clone | |
983 (src.header_ptr() | |
984 ,this->header_ptr() | |
985 ,detail::node_cloner <Cloner, value_traits, AlgoType, false>(cloner, &this->get_value_traits()) | |
986 ,detail::node_disposer<Disposer, value_traits, AlgoType>(disposer, &this->get_value_traits())); | |
987 this->sz_traits().set_size(src.sz_traits().get_size()); | |
988 this->comp() = src.comp(); | |
989 rollback.release(); | |
990 } | |
991 } | |
992 | |
842 //! <b>Requires</b>: value must be an lvalue | 993 //! <b>Requires</b>: value must be an lvalue |
843 //! | 994 //! |
844 //! <b>Effects</b>: Inserts value into the container before the upper bound. | 995 //! <b>Effects</b>: Inserts value into the container before the upper bound. |
845 //! | 996 //! |
846 //! <b>Complexity</b>: Average complexity for insert element is at | 997 //! <b>Complexity</b>: Average complexity for insert element is at |
850 //! | 1001 //! |
851 //! <b>Note</b>: Does not affect the validity of iterators and references. | 1002 //! <b>Note</b>: Does not affect the validity of iterators and references. |
852 //! No copy-constructors are called. | 1003 //! No copy-constructors are called. |
853 iterator insert_equal(reference value) | 1004 iterator insert_equal(reference value) |
854 { | 1005 { |
855 detail::key_nodeptr_comp<value_compare, real_value_traits> | 1006 detail::key_nodeptr_comp<value_compare, value_traits> |
856 key_node_comp(this->comp(), &this->get_real_value_traits()); | 1007 key_node_comp(this->comp(), &this->get_value_traits()); |
857 node_ptr to_insert(this->get_real_value_traits().to_node_ptr(value)); | 1008 node_ptr to_insert(this->get_value_traits().to_node_ptr(value)); |
858 if(safemode_or_autounlink) | 1009 if(safemode_or_autounlink) |
859 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); | 1010 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); |
860 iterator ret(node_algorithms::insert_equal_upper_bound | 1011 iterator ret(node_algorithms::insert_equal_upper_bound |
861 (this->header_ptr(), to_insert, key_node_comp), this->real_value_traits_ptr()); | 1012 (this->header_ptr(), to_insert, key_node_comp), this->priv_value_traits_ptr()); |
862 this->sz_traits().increment(); | 1013 this->sz_traits().increment(); |
863 return ret; | 1014 return ret; |
864 } | 1015 } |
865 | 1016 |
866 //! <b>Requires</b>: value must be an lvalue, and "hint" must be | 1017 //! <b>Requires</b>: value must be an lvalue, and "hint" must be |
877 //! | 1028 //! |
878 //! <b>Note</b>: Does not affect the validity of iterators and references. | 1029 //! <b>Note</b>: Does not affect the validity of iterators and references. |
879 //! No copy-constructors are called. | 1030 //! No copy-constructors are called. |
880 iterator insert_equal(const_iterator hint, reference value) | 1031 iterator insert_equal(const_iterator hint, reference value) |
881 { | 1032 { |
882 detail::key_nodeptr_comp<value_compare, real_value_traits> | 1033 detail::key_nodeptr_comp<value_compare, value_traits> |
883 key_node_comp(this->comp(), &this->get_real_value_traits()); | 1034 key_node_comp(this->comp(), &this->get_value_traits()); |
884 node_ptr to_insert(this->get_real_value_traits().to_node_ptr(value)); | 1035 node_ptr to_insert(this->get_value_traits().to_node_ptr(value)); |
885 if(safemode_or_autounlink) | 1036 if(safemode_or_autounlink) |
886 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); | 1037 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); |
887 iterator ret(node_algorithms::insert_equal | 1038 iterator ret(node_algorithms::insert_equal |
888 (this->header_ptr(), hint.pointed_node(), to_insert, key_node_comp), this->real_value_traits_ptr()); | 1039 (this->header_ptr(), hint.pointed_node(), to_insert, key_node_comp), this->priv_value_traits_ptr()); |
889 this->sz_traits().increment(); | 1040 this->sz_traits().increment(); |
890 return ret; | 1041 return ret; |
891 } | 1042 } |
892 | 1043 |
893 //! <b>Requires</b>: Dereferencing iterator must yield an lvalue | 1044 //! <b>Requires</b>: Dereferencing iterator must yield an lvalue |
1075 //! <b>Notes</b>: This function has only sense if a "insert_check" has been | 1226 //! <b>Notes</b>: This function has only sense if a "insert_check" has been |
1076 //! previously executed to fill "commit_data". No value should be inserted or | 1227 //! previously executed to fill "commit_data". No value should be inserted or |
1077 //! erased between the "insert_check" and "insert_commit" calls. | 1228 //! erased between the "insert_check" and "insert_commit" calls. |
1078 iterator insert_unique_commit(reference value, const insert_commit_data &commit_data) | 1229 iterator insert_unique_commit(reference value, const insert_commit_data &commit_data) |
1079 { | 1230 { |
1080 node_ptr to_insert(this->get_real_value_traits().to_node_ptr(value)); | 1231 node_ptr to_insert(this->get_value_traits().to_node_ptr(value)); |
1081 if(safemode_or_autounlink) | 1232 if(safemode_or_autounlink) |
1082 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); | 1233 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); |
1083 node_algorithms::insert_unique_commit | 1234 node_algorithms::insert_unique_commit |
1084 (this->header_ptr(), to_insert, commit_data); | 1235 (this->header_ptr(), to_insert, commit_data); |
1085 this->sz_traits().increment(); | 1236 this->sz_traits().increment(); |
1086 return iterator(to_insert, this->real_value_traits_ptr()); | 1237 return iterator(to_insert, this->priv_value_traits_ptr()); |
1087 } | 1238 } |
1088 | 1239 |
1089 //! <b>Requires</b>: value must be an lvalue, "pos" must be | 1240 //! <b>Requires</b>: value must be an lvalue, "pos" must be |
1090 //! a valid iterator (or end) and must be the succesor of value | 1241 //! a valid iterator (or end) and must be the succesor of value |
1091 //! once inserted according to the predicate | 1242 //! once inserted according to the predicate |
1100 //! the successor of "value" container ordering invariant will be broken. | 1251 //! the successor of "value" container ordering invariant will be broken. |
1101 //! This is a low-level function to be used only for performance reasons | 1252 //! This is a low-level function to be used only for performance reasons |
1102 //! by advanced users. | 1253 //! by advanced users. |
1103 iterator insert_before(const_iterator pos, reference value) | 1254 iterator insert_before(const_iterator pos, reference value) |
1104 { | 1255 { |
1105 node_ptr to_insert(this->get_real_value_traits().to_node_ptr(value)); | 1256 node_ptr to_insert(this->get_value_traits().to_node_ptr(value)); |
1106 if(safemode_or_autounlink) | 1257 if(safemode_or_autounlink) |
1107 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); | 1258 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); |
1108 this->sz_traits().increment(); | 1259 this->sz_traits().increment(); |
1109 return iterator(node_algorithms::insert_before | 1260 return iterator(node_algorithms::insert_before |
1110 (this->header_ptr(), pos.pointed_node(), to_insert), this->real_value_traits_ptr()); | 1261 (this->header_ptr(), pos.pointed_node(), to_insert), this->priv_value_traits_ptr()); |
1111 } | 1262 } |
1112 | 1263 |
1113 //! <b>Requires</b>: value must be an lvalue, and it must be no less | 1264 //! <b>Requires</b>: value must be an lvalue, and it must be no less |
1114 //! than the greatest inserted key | 1265 //! than the greatest inserted key |
1115 //! | 1266 //! |
1124 //! This function is slightly more efficient than using "insert_before". | 1275 //! This function is slightly more efficient than using "insert_before". |
1125 //! This is a low-level function to be used only for performance reasons | 1276 //! This is a low-level function to be used only for performance reasons |
1126 //! by advanced users. | 1277 //! by advanced users. |
1127 void push_back(reference value) | 1278 void push_back(reference value) |
1128 { | 1279 { |
1129 node_ptr to_insert(this->get_real_value_traits().to_node_ptr(value)); | 1280 node_ptr to_insert(this->get_value_traits().to_node_ptr(value)); |
1130 if(safemode_or_autounlink) | 1281 if(safemode_or_autounlink) |
1131 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); | 1282 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); |
1132 this->sz_traits().increment(); | 1283 this->sz_traits().increment(); |
1133 node_algorithms::push_back(this->header_ptr(), to_insert); | 1284 node_algorithms::push_back(this->header_ptr(), to_insert); |
1134 } | 1285 } |
1147 //! This function is slightly more efficient than using "insert_before". | 1298 //! This function is slightly more efficient than using "insert_before". |
1148 //! This is a low-level function to be used only for performance reasons | 1299 //! This is a low-level function to be used only for performance reasons |
1149 //! by advanced users. | 1300 //! by advanced users. |
1150 void push_front(reference value) | 1301 void push_front(reference value) |
1151 { | 1302 { |
1152 node_ptr to_insert(this->get_real_value_traits().to_node_ptr(value)); | 1303 node_ptr to_insert(this->get_value_traits().to_node_ptr(value)); |
1153 if(safemode_or_autounlink) | 1304 if(safemode_or_autounlink) |
1154 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); | 1305 BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert)); |
1155 this->sz_traits().increment(); | 1306 this->sz_traits().increment(); |
1156 node_algorithms::push_front(this->header_ptr(), to_insert); | 1307 node_algorithms::push_front(this->header_ptr(), to_insert); |
1157 } | 1308 } |
1158 | 1309 |
1159 //! <b>Effects</b>: Erases the element pointed to by pos. | 1310 //! <b>Effects</b>: Erases the element pointed to by i. |
1160 //! | 1311 //! |
1161 //! <b>Complexity</b>: Average complexity for erase element is constant time. | 1312 //! <b>Complexity</b>: Average complexity for erase element is constant time. |
1162 //! | 1313 //! |
1163 //! <b>Throws</b>: Nothing. | 1314 //! <b>Throws</b>: Nothing. |
1164 //! | 1315 //! |
1227 return n; | 1378 return n; |
1228 } | 1379 } |
1229 | 1380 |
1230 //! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw. | 1381 //! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw. |
1231 //! | 1382 //! |
1232 //! <b>Effects</b>: Erases the element pointed to by pos. | 1383 //! <b>Effects</b>: Erases the element pointed to by i. |
1233 //! Disposer::operator()(pointer) is called for the removed element. | 1384 //! Disposer::operator()(pointer) is called for the removed element. |
1234 //! | 1385 //! |
1235 //! <b>Complexity</b>: Average complexity for erase element is constant time. | 1386 //! <b>Complexity</b>: Average complexity for erase element is constant time. |
1236 //! | 1387 //! |
1237 //! <b>Throws</b>: Nothing. | 1388 //! <b>Throws</b>: Nothing. |
1241 template<class Disposer> | 1392 template<class Disposer> |
1242 iterator erase_and_dispose(const_iterator i, Disposer disposer) | 1393 iterator erase_and_dispose(const_iterator i, Disposer disposer) |
1243 { | 1394 { |
1244 node_ptr to_erase(i.pointed_node()); | 1395 node_ptr to_erase(i.pointed_node()); |
1245 iterator ret(this->erase(i)); | 1396 iterator ret(this->erase(i)); |
1246 disposer(this->get_real_value_traits().to_value_ptr(to_erase)); | 1397 disposer(this->get_value_traits().to_value_ptr(to_erase)); |
1247 return ret; | 1398 return ret; |
1248 } | 1399 } |
1249 | 1400 |
1250 #if !defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 1401 #if !defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1251 template<class Disposer> | 1402 template<class Disposer> |
1349 //! to the erased elements. Calls N times to disposer functor. | 1500 //! to the erased elements. Calls N times to disposer functor. |
1350 template<class Disposer> | 1501 template<class Disposer> |
1351 void clear_and_dispose(Disposer disposer) | 1502 void clear_and_dispose(Disposer disposer) |
1352 { | 1503 { |
1353 node_algorithms::clear_and_dispose(this->header_ptr() | 1504 node_algorithms::clear_and_dispose(this->header_ptr() |
1354 , detail::node_disposer<Disposer, real_value_traits, AlgoType>(disposer, &this->get_real_value_traits())); | 1505 , detail::node_disposer<Disposer, value_traits, AlgoType>(disposer, &this->get_value_traits())); |
1355 node_algorithms::init_header(this->header_ptr()); | 1506 node_algorithms::init_header(this->header_ptr()); |
1356 this->sz_traits().set_size(0); | 1507 this->sz_traits().set_size(0); |
1357 } | 1508 } |
1358 | 1509 |
1359 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | |
1360 | |
1361 //! <b>Effects</b>: Returns the number of contained elements with the given value | 1510 //! <b>Effects</b>: Returns the number of contained elements with the given value |
1362 //! | 1511 //! |
1363 //! <b>Complexity</b>: Logarithmic to the number of elements contained plus lineal | 1512 //! <b>Complexity</b>: Logarithmic to the number of elements contained plus lineal |
1364 //! to number of objects with the given value. | 1513 //! to number of objects with the given value. |
1365 //! | 1514 //! |
1366 //! <b>Throws</b>: Nothing. | 1515 //! <b>Throws</b>: If `value_compare` throws. |
1367 size_type count(const_reference value) const; | 1516 size_type count(const_reference value) const |
1517 { return size_type(this->count(value, this->comp())); } | |
1368 | 1518 |
1369 //! <b>Effects</b>: Returns the number of contained elements with the given key | 1519 //! <b>Effects</b>: Returns the number of contained elements with the given key |
1370 //! | 1520 //! |
1371 //! <b>Complexity</b>: Logarithmic to the number of elements contained plus lineal | 1521 //! <b>Complexity</b>: Logarithmic to the number of elements contained plus lineal |
1372 //! to number of objects with the given key. | 1522 //! to number of objects with the given key. |
1373 //! | 1523 //! |
1374 //! <b>Throws</b>: Nothing. | 1524 //! <b>Throws</b>: If `comp` throws. |
1375 template<class KeyType, class KeyValueCompare> | 1525 template<class KeyType, class KeyValueCompare> |
1376 size_type count(const KeyType &key, KeyValueCompare comp) const; | 1526 size_type count(const KeyType &key, KeyValueCompare comp) const |
1527 { | |
1528 std::pair<const_iterator, const_iterator> ret = this->equal_range(key, comp); | |
1529 size_type n = 0; | |
1530 for(; ret.first != ret.second; ++ret.first){ ++n; } | |
1531 return n; | |
1532 } | |
1533 | |
1534 #if !defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | |
1535 | |
1536 //Add non-const overloads to theoretically const members | |
1537 //as some algorithms have different behavior when non-const versions are used (like splay trees). | |
1538 size_type count(const_reference value) | |
1539 { return size_type(this->count(value, this->comp())); } | |
1540 | |
1541 template<class KeyType, class KeyValueCompare> | |
1542 size_type count(const KeyType &key, KeyValueCompare comp) | |
1543 { | |
1544 std::pair<const_iterator, const_iterator> ret = this->equal_range(key, comp); | |
1545 size_type n = 0; | |
1546 for(; ret.first != ret.second; ++ret.first){ ++n; } | |
1547 return n; | |
1548 } | |
1549 | |
1550 #else //defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | |
1377 | 1551 |
1378 //! <b>Effects</b>: Returns an iterator to the first element whose | 1552 //! <b>Effects</b>: Returns an iterator to the first element whose |
1379 //! key is not less than k or end() if that element does not exist. | 1553 //! key is not less than k or end() if that element does not exist. |
1380 //! | 1554 //! |
1381 //! <b>Complexity</b>: Logarithmic. | 1555 //! <b>Complexity</b>: Logarithmic. |
1382 //! | 1556 //! |
1383 //! <b>Throws</b>: Nothing. | 1557 //! <b>Throws</b>: If `value_compare` throws. |
1384 iterator lower_bound(const_reference value); | 1558 iterator lower_bound(const_reference value); |
1385 | 1559 |
1386 //! <b>Effects</b>: Returns an iterator to the first element whose | 1560 //! <b>Effects</b>: Returns an iterator to the first element whose |
1387 //! key is not less than k or end() if that element does not exist. | 1561 //! key is not less than k or end() if that element does not exist. |
1388 //! | 1562 //! |
1389 //! <b>Complexity</b>: Logarithmic. | 1563 //! <b>Complexity</b>: Logarithmic. |
1390 //! | 1564 //! |
1391 //! <b>Throws</b>: Nothing. | 1565 //! <b>Throws</b>: If `value_compare` throws. |
1392 const_iterator lower_bound(const_reference value) const; | 1566 const_iterator lower_bound(const_reference value) const; |
1393 | 1567 |
1394 //! <b>Effects</b>: Returns an iterator to the first element whose | 1568 //! <b>Effects</b>: Returns an iterator to the first element whose |
1395 //! key is not less than k or end() if that element does not exist. | 1569 //! key is not less than k or end() if that element does not exist. |
1396 //! | 1570 //! |
1397 //! <b>Complexity</b>: Logarithmic. | 1571 //! <b>Complexity</b>: Logarithmic. |
1398 //! | 1572 //! |
1399 //! <b>Throws</b>: Nothing. | 1573 //! <b>Throws</b>: If `comp` throws. |
1400 template<class KeyType, class KeyValueCompare> | 1574 template<class KeyType, class KeyValueCompare> |
1401 iterator lower_bound(const KeyType &key, KeyValueCompare comp); | 1575 iterator lower_bound(const KeyType &key, KeyValueCompare comp); |
1402 | 1576 |
1403 //! <b>Effects</b>: Returns a const iterator to the first element whose | 1577 //! <b>Effects</b>: Returns a const iterator to the first element whose |
1404 //! key is not less than k or end() if that element does not exist. | 1578 //! key is not less than k or end() if that element does not exist. |
1405 //! | 1579 //! |
1406 //! <b>Complexity</b>: Logarithmic. | 1580 //! <b>Complexity</b>: Logarithmic. |
1407 //! | 1581 //! |
1408 //! <b>Throws</b>: Nothing. | 1582 //! <b>Throws</b>: If `comp` throws. |
1409 template<class KeyType, class KeyValueCompare> | 1583 template<class KeyType, class KeyValueCompare> |
1410 const_iterator lower_bound(const KeyType &key, KeyValueCompare comp) const; | 1584 const_iterator lower_bound(const KeyType &key, KeyValueCompare comp) const; |
1411 | 1585 |
1412 //! <b>Effects</b>: Returns an iterator to the first element whose | 1586 //! <b>Effects</b>: Returns an iterator to the first element whose |
1413 //! key is greater than k or end() if that element does not exist. | 1587 //! key is greater than k or end() if that element does not exist. |
1414 //! | 1588 //! |
1415 //! <b>Complexity</b>: Logarithmic. | 1589 //! <b>Complexity</b>: Logarithmic. |
1416 //! | 1590 //! |
1417 //! <b>Throws</b>: Nothing. | 1591 //! <b>Throws</b>: If `value_compare` throws. |
1418 iterator upper_bound(const_reference value); | 1592 iterator upper_bound(const_reference value); |
1419 | 1593 |
1420 //! <b>Effects</b>: Returns an iterator to the first element whose | 1594 //! <b>Effects</b>: Returns an iterator to the first element whose |
1421 //! key is greater than k according to comp or end() if that element | 1595 //! key is greater than k according to comp or end() if that element |
1422 //! does not exist. | 1596 //! does not exist. |
1423 //! | 1597 //! |
1424 //! <b>Complexity</b>: Logarithmic. | 1598 //! <b>Complexity</b>: Logarithmic. |
1425 //! | 1599 //! |
1426 //! <b>Throws</b>: Nothing. | 1600 //! <b>Throws</b>: If `comp` throws. |
1427 template<class KeyType, class KeyValueCompare> | 1601 template<class KeyType, class KeyValueCompare> |
1428 iterator upper_bound(const KeyType &key, KeyValueCompare comp); | 1602 iterator upper_bound(const KeyType &key, KeyValueCompare comp); |
1429 | 1603 |
1430 //! <b>Effects</b>: Returns an iterator to the first element whose | 1604 //! <b>Effects</b>: Returns an iterator to the first element whose |
1431 //! key is greater than k or end() if that element does not exist. | 1605 //! key is greater than k or end() if that element does not exist. |
1432 //! | 1606 //! |
1433 //! <b>Complexity</b>: Logarithmic. | 1607 //! <b>Complexity</b>: Logarithmic. |
1434 //! | 1608 //! |
1435 //! <b>Throws</b>: Nothing. | 1609 //! <b>Throws</b>: If `value_compare` throws. |
1436 const_iterator upper_bound(const_reference value) const; | 1610 const_iterator upper_bound(const_reference value) const; |
1437 | 1611 |
1438 //! <b>Effects</b>: Returns an iterator to the first element whose | 1612 //! <b>Effects</b>: Returns an iterator to the first element whose |
1439 //! key is greater than k according to comp or end() if that element | 1613 //! key is greater than k according to comp or end() if that element |
1440 //! does not exist. | 1614 //! does not exist. |
1441 //! | 1615 //! |
1442 //! <b>Complexity</b>: Logarithmic. | 1616 //! <b>Complexity</b>: Logarithmic. |
1443 //! | 1617 //! |
1444 //! <b>Throws</b>: Nothing. | 1618 //! <b>Throws</b>: If `comp` throws. |
1445 template<class KeyType, class KeyValueCompare> | 1619 template<class KeyType, class KeyValueCompare> |
1446 const_iterator upper_bound(const KeyType &key, KeyValueCompare comp) const; | 1620 const_iterator upper_bound(const KeyType &key, KeyValueCompare comp) const; |
1447 | 1621 |
1448 //! <b>Effects</b>: Finds an iterator to the first element whose key is | 1622 //! <b>Effects</b>: Finds an iterator to the first element whose key is |
1449 //! k or end() if that element does not exist. | 1623 //! k or end() if that element does not exist. |
1450 //! | 1624 //! |
1451 //! <b>Complexity</b>: Logarithmic. | 1625 //! <b>Complexity</b>: Logarithmic. |
1452 //! | 1626 //! |
1453 //! <b>Throws</b>: Nothing. | 1627 //! <b>Throws</b>: If `value_compare` throws. |
1454 iterator find(const_reference value); | 1628 iterator find(const_reference value); |
1455 | 1629 |
1456 //! <b>Effects</b>: Finds an iterator to the first element whose key is | 1630 //! <b>Effects</b>: Finds an iterator to the first element whose key is |
1457 //! k or end() if that element does not exist. | 1631 //! k or end() if that element does not exist. |
1458 //! | 1632 //! |
1459 //! <b>Complexity</b>: Logarithmic. | 1633 //! <b>Complexity</b>: Logarithmic. |
1460 //! | 1634 //! |
1461 //! <b>Throws</b>: Nothing. | 1635 //! <b>Throws</b>: If `comp` throws. |
1462 template<class KeyType, class KeyValueCompare> | 1636 template<class KeyType, class KeyValueCompare> |
1463 iterator find(const KeyType &key, KeyValueCompare comp); | 1637 iterator find(const KeyType &key, KeyValueCompare comp); |
1464 | 1638 |
1465 //! <b>Effects</b>: Finds a const_iterator to the first element whose key is | 1639 //! <b>Effects</b>: Finds a const_iterator to the first element whose key is |
1466 //! k or end() if that element does not exist. | 1640 //! k or end() if that element does not exist. |
1467 //! | 1641 //! |
1468 //! <b>Complexity</b>: Logarithmic. | 1642 //! <b>Complexity</b>: Logarithmic. |
1469 //! | 1643 //! |
1470 //! <b>Throws</b>: Nothing. | 1644 //! <b>Throws</b>: If `value_compare` throws. |
1471 const_iterator find(const_reference value) const; | 1645 const_iterator find(const_reference value) const; |
1472 | 1646 |
1473 //! <b>Effects</b>: Finds a const_iterator to the first element whose key is | 1647 //! <b>Effects</b>: Finds a const_iterator to the first element whose key is |
1474 //! k or end() if that element does not exist. | 1648 //! k or end() if that element does not exist. |
1475 //! | 1649 //! |
1476 //! <b>Complexity</b>: Logarithmic. | 1650 //! <b>Complexity</b>: Logarithmic. |
1477 //! | 1651 //! |
1478 //! <b>Throws</b>: Nothing. | 1652 //! <b>Throws</b>: If `comp` throws. |
1479 template<class KeyType, class KeyValueCompare> | 1653 template<class KeyType, class KeyValueCompare> |
1480 const_iterator find(const KeyType &key, KeyValueCompare comp) const; | 1654 const_iterator find(const KeyType &key, KeyValueCompare comp) const; |
1481 | 1655 |
1482 //! <b>Effects</b>: Finds a range containing all elements whose key is k or | 1656 //! <b>Effects</b>: Finds a range containing all elements whose key is k or |
1483 //! an empty range that indicates the position where those elements would be | 1657 //! an empty range that indicates the position where those elements would be |
1484 //! if they there is no elements with key k. | 1658 //! if they there is no elements with key k. |
1485 //! | 1659 //! |
1486 //! <b>Complexity</b>: Logarithmic. | 1660 //! <b>Complexity</b>: Logarithmic. |
1487 //! | 1661 //! |
1488 //! <b>Throws</b>: Nothing. | 1662 //! <b>Throws</b>: If `value_compare` throws. |
1489 std::pair<iterator,iterator> equal_range(const_reference value); | 1663 std::pair<iterator,iterator> equal_range(const_reference value); |
1490 | 1664 |
1491 //! <b>Effects</b>: Finds a range containing all elements whose key is k or | 1665 //! <b>Effects</b>: Finds a range containing all elements whose key is k or |
1492 //! an empty range that indicates the position where those elements would be | 1666 //! an empty range that indicates the position where those elements would be |
1493 //! if they there is no elements with key k. | 1667 //! if they there is no elements with key k. |
1494 //! | 1668 //! |
1495 //! <b>Complexity</b>: Logarithmic. | 1669 //! <b>Complexity</b>: Logarithmic. |
1496 //! | 1670 //! |
1497 //! <b>Throws</b>: Nothing. | 1671 //! <b>Throws</b>: If `comp` throws. |
1498 template<class KeyType, class KeyValueCompare> | 1672 template<class KeyType, class KeyValueCompare> |
1499 std::pair<iterator,iterator> equal_range(const KeyType &key, KeyValueCompare comp); | 1673 std::pair<iterator,iterator> equal_range(const KeyType &key, KeyValueCompare comp); |
1500 | 1674 |
1501 //! <b>Effects</b>: Finds a range containing all elements whose key is k or | 1675 //! <b>Effects</b>: Finds a range containing all elements whose key is k or |
1502 //! an empty range that indicates the position where those elements would be | 1676 //! an empty range that indicates the position where those elements would be |
1503 //! if they there is no elements with key k. | 1677 //! if they there is no elements with key k. |
1504 //! | 1678 //! |
1505 //! <b>Complexity</b>: Logarithmic. | 1679 //! <b>Complexity</b>: Logarithmic. |
1506 //! | 1680 //! |
1507 //! <b>Throws</b>: Nothing. | 1681 //! <b>Throws</b>: If `value_compare` throws. |
1508 std::pair<const_iterator, const_iterator> | 1682 std::pair<const_iterator, const_iterator> |
1509 equal_range(const_reference value) const; | 1683 equal_range(const_reference value) const; |
1510 | 1684 |
1511 //! <b>Effects</b>: Finds a range containing all elements whose key is k or | 1685 //! <b>Effects</b>: Finds a range containing all elements whose key is k or |
1512 //! an empty range that indicates the position where those elements would be | 1686 //! an empty range that indicates the position where those elements would be |
1513 //! if they there is no elements with key k. | 1687 //! if they there is no elements with key k. |
1514 //! | 1688 //! |
1515 //! <b>Complexity</b>: Logarithmic. | 1689 //! <b>Complexity</b>: Logarithmic. |
1516 //! | 1690 //! |
1517 //! <b>Throws</b>: Nothing. | 1691 //! <b>Throws</b>: If `comp` throws. |
1518 template<class KeyType, class KeyValueCompare> | 1692 template<class KeyType, class KeyValueCompare> |
1519 std::pair<const_iterator, const_iterator> | 1693 std::pair<const_iterator, const_iterator> |
1520 equal_range(const KeyType &key, KeyValueCompare comp) const; | 1694 equal_range(const KeyType &key, KeyValueCompare comp) const; |
1521 | 1695 |
1522 //! <b>Requires</b>: 'lower_value' must not be greater than 'upper_value'. If | 1696 //! <b>Requires</b>: 'lower_value' must not be greater than 'upper_value'. If |
1528 //! | 1702 //! |
1529 //! second = upper_bound(upper_key) if right_closed, lower_bound(upper_key) otherwise | 1703 //! second = upper_bound(upper_key) if right_closed, lower_bound(upper_key) otherwise |
1530 //! | 1704 //! |
1531 //! <b>Complexity</b>: Logarithmic. | 1705 //! <b>Complexity</b>: Logarithmic. |
1532 //! | 1706 //! |
1533 //! <b>Throws</b>: If the predicate throws. | 1707 //! <b>Throws</b>: If `value_compare` throws. |
1534 //! | 1708 //! |
1535 //! <b>Note</b>: This function can be more efficient than calling upper_bound | 1709 //! <b>Note</b>: This function can be more efficient than calling upper_bound |
1536 //! and lower_bound for lower_value and upper_value. | 1710 //! and lower_bound for lower_value and upper_value. |
1537 //! | 1711 //! |
1538 //! <b>Note</b>: Experimental function, the interface might change in future releases. | 1712 //! <b>Note</b>: Experimental function, the interface might change in future releases. |
1539 std::pair<iterator,iterator> bounded_range | 1713 std::pair<iterator,iterator> bounded_range |
1540 (const_reference lower_value, const_reference upper_value, bool left_closed, bool right_closed); | 1714 (const_reference lower_value, const_reference upper_value, bool left_closed, bool right_closed); |
1541 | 1715 |
1542 //! <b>Requires</b>: KeyValueCompare is a function object that induces a strict weak | 1716 //! <b>Requires</b>: KeyValueCompare is a function object that induces a strict weak |
1543 //! ordering compatible with the strict weak ordering used to create the | 1717 //! ordering compatible with the strict weak ordering used to create the |
1544 //! the container. | 1718 //! the container. |
1545 //! 'lower_key' must not be greater than 'upper_key' according to 'comp'. If | 1719 //! 'lower_key' must not be greater than 'upper_key' according to 'comp'. If |
1546 //! 'lower_key' == 'upper_key', ('left_closed' || 'right_closed') must be false. | 1720 //! 'lower_key' == 'upper_key', ('left_closed' || 'right_closed') must be false. |
1547 //! | 1721 //! |
1548 //! <b>Effects</b>: Returns an a pair with the following criteria: | 1722 //! <b>Effects</b>: Returns an a pair with the following criteria: |
1549 //! | 1723 //! |
1551 //! | 1725 //! |
1552 //! second = upper_bound(upper_key, comp) if right_closed, lower_bound(upper_key, comp) otherwise | 1726 //! second = upper_bound(upper_key, comp) if right_closed, lower_bound(upper_key, comp) otherwise |
1553 //! | 1727 //! |
1554 //! <b>Complexity</b>: Logarithmic. | 1728 //! <b>Complexity</b>: Logarithmic. |
1555 //! | 1729 //! |
1556 //! <b>Throws</b>: If "comp" throws. | 1730 //! <b>Throws</b>: If `comp` throws. |
1557 //! | 1731 //! |
1558 //! <b>Note</b>: This function can be more efficient than calling upper_bound | 1732 //! <b>Note</b>: This function can be more efficient than calling upper_bound |
1559 //! and lower_bound for lower_key and upper_key. | 1733 //! and lower_bound for lower_key and upper_key. |
1560 //! | 1734 //! |
1561 //! <b>Note</b>: Experimental function, the interface might change in future releases. | 1735 //! <b>Note</b>: Experimental function, the interface might change in future releases. |
1572 //! | 1746 //! |
1573 //! second = upper_bound(upper_key) if right_closed, lower_bound(upper_key) otherwise | 1747 //! second = upper_bound(upper_key) if right_closed, lower_bound(upper_key) otherwise |
1574 //! | 1748 //! |
1575 //! <b>Complexity</b>: Logarithmic. | 1749 //! <b>Complexity</b>: Logarithmic. |
1576 //! | 1750 //! |
1577 //! <b>Throws</b>: If the predicate throws. | 1751 //! <b>Throws</b>: If `value_compare` throws. |
1578 //! | 1752 //! |
1579 //! <b>Note</b>: This function can be more efficient than calling upper_bound | 1753 //! <b>Note</b>: This function can be more efficient than calling upper_bound |
1580 //! and lower_bound for lower_value and upper_value. | 1754 //! and lower_bound for lower_value and upper_value. |
1581 //! | 1755 //! |
1582 //! <b>Note</b>: Experimental function, the interface might change in future releases. | 1756 //! <b>Note</b>: Experimental function, the interface might change in future releases. |
1583 std::pair<const_iterator,const_iterator> bounded_range | 1757 std::pair<const_iterator,const_iterator> bounded_range |
1584 (const_reference lower_value, const_reference upper_value, bool left_closed, bool right_closed) const; | 1758 (const_reference lower_value, const_reference upper_value, bool left_closed, bool right_closed) const; |
1585 | 1759 |
1586 //! <b>Requires</b>: KeyValueCompare is a function object that induces a strict weak | 1760 //! <b>Requires</b>: KeyValueCompare is a function object that induces a strict weak |
1587 //! ordering compatible with the strict weak ordering used to create the | 1761 //! ordering compatible with the strict weak ordering used to create the |
1588 //! the container. | 1762 //! the container. |
1589 //! 'lower_key' must not be greater than 'upper_key' according to 'comp'. If | 1763 //! 'lower_key' must not be greater than 'upper_key' according to 'comp'. If |
1590 //! 'lower_key' == 'upper_key', ('left_closed' || 'right_closed') must be false. | 1764 //! 'lower_key' == 'upper_key', ('left_closed' || 'right_closed') must be false. |
1591 //! | 1765 //! |
1592 //! <b>Effects</b>: Returns an a pair with the following criteria: | 1766 //! <b>Effects</b>: Returns an a pair with the following criteria: |
1593 //! | 1767 //! |
1595 //! | 1769 //! |
1596 //! second = upper_bound(upper_key, comp) if right_closed, lower_bound(upper_key, comp) otherwise | 1770 //! second = upper_bound(upper_key, comp) if right_closed, lower_bound(upper_key, comp) otherwise |
1597 //! | 1771 //! |
1598 //! <b>Complexity</b>: Logarithmic. | 1772 //! <b>Complexity</b>: Logarithmic. |
1599 //! | 1773 //! |
1600 //! <b>Throws</b>: If "comp" throws. | 1774 //! <b>Throws</b>: If `comp` throws. |
1601 //! | 1775 //! |
1602 //! <b>Note</b>: This function can be more efficient than calling upper_bound | 1776 //! <b>Note</b>: This function can be more efficient than calling upper_bound |
1603 //! and lower_bound for lower_key and upper_key. | 1777 //! and lower_bound for lower_key and upper_key. |
1604 //! | 1778 //! |
1605 //! <b>Note</b>: Experimental function, the interface might change in future releases. | 1779 //! <b>Note</b>: Experimental function, the interface might change in future releases. |
1689 if(!to_be_disposed) | 1863 if(!to_be_disposed) |
1690 return 0; | 1864 return 0; |
1691 this->sz_traits().decrement(); | 1865 this->sz_traits().decrement(); |
1692 if(safemode_or_autounlink)//If this is commented does not work with normal_link | 1866 if(safemode_or_autounlink)//If this is commented does not work with normal_link |
1693 node_algorithms::init(to_be_disposed); | 1867 node_algorithms::init(to_be_disposed); |
1694 return this->get_real_value_traits().to_value_ptr(to_be_disposed); | 1868 return this->get_value_traits().to_value_ptr(to_be_disposed); |
1695 } | 1869 } |
1696 | 1870 |
1697 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 1871 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1698 | 1872 |
1699 //! <b>Requires</b>: replace_this must be a valid iterator of *this | 1873 //! <b>Requires</b>: replace_this must be a valid iterator of *this |
1751 node_algorithms::unlink(to_remove); | 1925 node_algorithms::unlink(to_remove); |
1752 if(safemode_or_autounlink) | 1926 if(safemode_or_autounlink) |
1753 node_algorithms::init(to_remove); | 1927 node_algorithms::init(to_remove); |
1754 } | 1928 } |
1755 | 1929 |
1930 //! <b>Effects</b>: Asserts the integrity of the container with additional checks provided by the user. | |
1931 //! | |
1932 //! <b>Complexity</b>: Linear time. | |
1933 //! | |
1934 //! <b>Note</b>: The method might not have effect when asserts are turned off (e.g., with NDEBUG). | |
1935 //! Experimental function, interface might change in future versions. | |
1936 template <class ExtraChecker> | |
1937 void check(ExtraChecker extra_checker) const | |
1938 { | |
1939 typedef detail::key_nodeptr_comp<value_compare, value_traits> nodeptr_comp_t; | |
1940 nodeptr_comp_t nodeptr_comp(this->comp(), &this->get_value_traits()); | |
1941 typedef typename get_node_checker<AlgoType, ValueTraits, nodeptr_comp_t, ExtraChecker>::type node_checker_t; | |
1942 typename node_checker_t::return_type checker_return; | |
1943 node_algorithms::check(this->header_ptr(), node_checker_t(nodeptr_comp, extra_checker), checker_return); | |
1944 if (constant_time_size) | |
1945 BOOST_INTRUSIVE_INVARIANT_ASSERT(this->sz_traits().get_size() == checker_return.node_count); | |
1946 } | |
1947 | |
1948 //! <b>Effects</b>: Asserts the integrity of the container. | |
1949 //! | |
1950 //! <b>Complexity</b>: Linear time. | |
1951 //! | |
1952 //! <b>Note</b>: The method has no effect when asserts are turned off (e.g., with NDEBUG). | |
1953 //! Experimental function, interface might change in future versions. | |
1954 void check() const | |
1955 { | |
1956 check(detail::empty_node_checker<ValueTraits>()); | |
1957 } | |
1958 | |
1756 /// @cond | 1959 /// @cond |
1757 private: | 1960 private: |
1758 template<class Disposer> | 1961 template<class Disposer> |
1759 iterator private_erase(const_iterator b, const_iterator e, size_type &n, Disposer disposer) | 1962 iterator private_erase(const_iterator b, const_iterator e, size_type &n, Disposer disposer) |
1760 { | 1963 { |
1768 for(n = 0; b != e; ++n) | 1971 for(n = 0; b != e; ++n) |
1769 this->erase(b++); | 1972 this->erase(b++); |
1770 return b.unconst(); | 1973 return b.unconst(); |
1771 } | 1974 } |
1772 /// @endcond | 1975 /// @endcond |
1773 | |
1774 private: | |
1775 static bstree_impl &priv_container_from_end_iterator(const const_iterator &end_iterator) | |
1776 { | |
1777 return *static_cast<bstree_impl*> | |
1778 (boost::intrusive::detail::to_raw_pointer(end_iterator.pointed_node())); | |
1779 } | |
1780 }; | 1976 }; |
1781 | 1977 |
1782 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 1978 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1783 template<class T, class ...Options> | 1979 template<class T, class ...Options> |
1784 #else | 1980 #else |
1785 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType> | 1981 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType, typename HeaderHolder> |
1786 #endif | 1982 #endif |
1787 inline bool operator< | 1983 inline bool operator< |
1788 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 1984 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1789 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) | 1985 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) |
1790 #else | 1986 #else |
1791 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &x | 1987 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &x |
1792 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &y) | 1988 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &y) |
1793 #endif | 1989 #endif |
1794 { return std::lexicographical_compare(x.begin(), x.end(), y.begin(), y.end()); } | 1990 { return ::boost::intrusive::algo_lexicographical_compare(x.begin(), x.end(), y.begin(), y.end()); } |
1795 | 1991 |
1796 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 1992 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1797 template<class T, class ...Options> | 1993 template<class T, class ...Options> |
1798 #else | 1994 #else |
1799 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType> | 1995 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType, typename HeaderHolder> |
1800 #endif | 1996 #endif |
1801 bool operator== | 1997 bool operator== |
1802 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 1998 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1803 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) | 1999 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) |
1804 #else | 2000 #else |
1805 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &x | 2001 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &x |
1806 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &y) | 2002 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &y) |
1807 #endif | 2003 #endif |
1808 { | 2004 { |
1809 typedef bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> tree_type; | 2005 typedef bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> tree_type; |
1810 typedef typename tree_type::const_iterator const_iterator; | |
1811 | 2006 |
1812 if(tree_type::constant_time_size && x.size() != y.size()){ | 2007 if(tree_type::constant_time_size && x.size() != y.size()){ |
1813 return false; | 2008 return false; |
1814 } | 2009 } |
1815 const_iterator end1 = x.end(); | 2010 return boost::intrusive::algo_equal(x.cbegin(), x.cend(), y.cbegin(), y.cend()); |
1816 const_iterator i1 = x.begin(); | |
1817 const_iterator i2 = y.begin(); | |
1818 if(tree_type::constant_time_size){ | |
1819 while (i1 != end1 && *i1 == *i2) { | |
1820 ++i1; | |
1821 ++i2; | |
1822 } | |
1823 return i1 == end1; | |
1824 } | |
1825 else{ | |
1826 const_iterator end2 = y.end(); | |
1827 while (i1 != end1 && i2 != end2 && *i1 == *i2) { | |
1828 ++i1; | |
1829 ++i2; | |
1830 } | |
1831 return i1 == end1 && i2 == end2; | |
1832 } | |
1833 } | 2011 } |
1834 | 2012 |
1835 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2013 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1836 template<class T, class ...Options> | 2014 template<class T, class ...Options> |
1837 #else | 2015 #else |
1838 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType> | 2016 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType, typename HeaderHolder> |
1839 #endif | 2017 #endif |
1840 inline bool operator!= | 2018 inline bool operator!= |
1841 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2019 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1842 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) | 2020 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) |
1843 #else | 2021 #else |
1844 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &x | 2022 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &x |
1845 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &y) | 2023 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &y) |
1846 #endif | 2024 #endif |
1847 { return !(x == y); } | 2025 { return !(x == y); } |
1848 | 2026 |
1849 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2027 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1850 template<class T, class ...Options> | 2028 template<class T, class ...Options> |
1851 #else | 2029 #else |
1852 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType> | 2030 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType, typename HeaderHolder> |
1853 #endif | 2031 #endif |
1854 inline bool operator> | 2032 inline bool operator> |
1855 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2033 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1856 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) | 2034 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) |
1857 #else | 2035 #else |
1858 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &x | 2036 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &x |
1859 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &y) | 2037 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &y) |
1860 #endif | 2038 #endif |
1861 { return y < x; } | 2039 { return y < x; } |
1862 | 2040 |
1863 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2041 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1864 template<class T, class ...Options> | 2042 template<class T, class ...Options> |
1865 #else | 2043 #else |
1866 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType> | 2044 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType, typename HeaderHolder> |
1867 #endif | 2045 #endif |
1868 inline bool operator<= | 2046 inline bool operator<= |
1869 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2047 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1870 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) | 2048 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) |
1871 #else | 2049 #else |
1872 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &x | 2050 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &x |
1873 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &y) | 2051 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &y) |
1874 #endif | 2052 #endif |
1875 { return !(y < x); } | 2053 { return !(y < x); } |
1876 | 2054 |
1877 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2055 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1878 template<class T, class ...Options> | 2056 template<class T, class ...Options> |
1879 #else | 2057 #else |
1880 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType> | 2058 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType, typename HeaderHolder> |
1881 #endif | 2059 #endif |
1882 inline bool operator>= | 2060 inline bool operator>= |
1883 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2061 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1884 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) | 2062 (const bstree_impl<T, Options...> &x, const bstree_impl<T, Options...> &y) |
1885 #else | 2063 #else |
1886 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &x | 2064 ( const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &x |
1887 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &y) | 2065 , const bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &y) |
1888 #endif | 2066 #endif |
1889 { return !(x < y); } | 2067 { return !(x < y); } |
1890 | 2068 |
1891 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2069 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1892 template<class T, class ...Options> | 2070 template<class T, class ...Options> |
1893 #else | 2071 #else |
1894 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType> | 2072 template<class ValueTraits, class VoidKeyComp, class SizeType, bool ConstantTimeSize, algo_types AlgoType, typename HeaderHolder> |
1895 #endif | 2073 #endif |
1896 inline void swap | 2074 inline void swap |
1897 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) | 2075 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) |
1898 (bstree_impl<T, Options...> &x, bstree_impl<T, Options...> &y) | 2076 (bstree_impl<T, Options...> &x, bstree_impl<T, Options...> &y) |
1899 #else | 2077 #else |
1900 ( bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &x | 2078 ( bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &x |
1901 , bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType> &y) | 2079 , bstree_impl<ValueTraits, VoidKeyComp, SizeType, ConstantTimeSize, AlgoType, HeaderHolder> &y) |
1902 #endif | 2080 #endif |
1903 { x.swap(y); } | 2081 { x.swap(y); } |
1904 | 2082 |
1905 //! Helper metafunction to define a \c bstree that yields to the same type when the | 2083 //! Helper metafunction to define a \c bstree that yields to the same type when the |
1906 //! same options (either explicitly or implicitly) are used. | 2084 //! same options (either explicitly or implicitly) are used. |
1907 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) || defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) | 2085 #if defined(BOOST_INTRUSIVE_DOXYGEN_INVOKED) || defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) |
1908 template<class T, class ...Options> | 2086 template<class T, class ...Options> |
1909 #else | 2087 #else |
1910 template<class T, class O1 = void, class O2 = void | 2088 template<class T, class O1 = void, class O2 = void |
1911 , class O3 = void, class O4 = void> | 2089 , class O3 = void, class O4 = void |
2090 , class O5 = void> | |
1912 #endif | 2091 #endif |
1913 struct make_bstree | 2092 struct make_bstree |
1914 { | 2093 { |
1915 /// @cond | 2094 /// @cond |
1916 typedef typename pack_options | 2095 typedef typename pack_options |
1917 < bstree_defaults, | 2096 < bstree_defaults, |
1918 #if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) | 2097 #if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) |
1919 O1, O2, O3, O4 | 2098 O1, O2, O3, O4, O5 |
1920 #else | 2099 #else |
1921 Options... | 2100 Options... |
1922 #endif | 2101 #endif |
1923 >::type packed_options; | 2102 >::type packed_options; |
1924 | 2103 |
1929 < value_traits | 2108 < value_traits |
1930 , typename packed_options::compare | 2109 , typename packed_options::compare |
1931 , typename packed_options::size_type | 2110 , typename packed_options::size_type |
1932 , packed_options::constant_time_size | 2111 , packed_options::constant_time_size |
1933 , BsTreeAlgorithms | 2112 , BsTreeAlgorithms |
2113 , typename packed_options::header_holder_type | |
1934 > implementation_defined; | 2114 > implementation_defined; |
1935 /// @endcond | 2115 /// @endcond |
1936 typedef implementation_defined type; | 2116 typedef implementation_defined type; |
1937 }; | 2117 }; |
1938 | 2118 |
1939 | 2119 |
1940 #ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED | 2120 #ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED |
1941 | 2121 |
1942 #if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) | 2122 #if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) |
1943 template<class T, class O1, class O2, class O3, class O4> | 2123 template<class T, class O1, class O2, class O3, class O4, class O5> |
1944 #else | 2124 #else |
1945 template<class T, class ...Options> | 2125 template<class T, class ...Options> |
1946 #endif | 2126 #endif |
1947 class bstree | 2127 class bstree |
1948 : public make_bstree<T, | 2128 : public make_bstree<T, |
1949 #if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) | 2129 #if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) |
1950 O1, O2, O3, O4 | 2130 O1, O2, O3, O4, O5 |
1951 #else | 2131 #else |
1952 Options... | 2132 Options... |
1953 #endif | 2133 #endif |
1954 >::type | 2134 >::type |
1955 { | 2135 { |
1956 typedef typename make_bstree | 2136 typedef typename make_bstree |
1957 <T, | 2137 <T, |
1958 #if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) | 2138 #if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES) |
1959 O1, O2, O3, O4 | 2139 O1, O2, O3, O4, O5 |
1960 #else | 2140 #else |
1961 Options... | 2141 Options... |
1962 #endif | 2142 #endif |
1963 >::type Base; | 2143 >::type Base; |
1964 BOOST_MOVABLE_BUT_NOT_COPYABLE(bstree) | 2144 BOOST_MOVABLE_BUT_NOT_COPYABLE(bstree) |
1965 | 2145 |
1966 public: | 2146 public: |
1967 typedef typename Base::value_compare value_compare; | 2147 typedef typename Base::value_compare value_compare; |
1968 typedef typename Base::value_traits value_traits; | 2148 typedef typename Base::value_traits value_traits; |
1969 typedef typename Base::real_value_traits real_value_traits; | |
1970 typedef typename Base::iterator iterator; | 2149 typedef typename Base::iterator iterator; |
1971 typedef typename Base::const_iterator const_iterator; | 2150 typedef typename Base::const_iterator const_iterator; |
1972 | 2151 |
1973 //Assert if passed value traits are compatible with the type | 2152 //Assert if passed value traits are compatible with the type |
1974 BOOST_STATIC_ASSERT((detail::is_same<typename real_value_traits::value_type, T>::value)); | 2153 BOOST_STATIC_ASSERT((detail::is_same<typename value_traits::value_type, T>::value)); |
1975 | 2154 |
1976 bstree( const value_compare &cmp = value_compare() | 2155 bstree( const value_compare &cmp = value_compare() |
1977 , const value_traits &v_traits = value_traits()) | 2156 , const value_traits &v_traits = value_traits()) |
1978 : Base(cmp, v_traits) | 2157 : Base(cmp, v_traits) |
1979 {} | 2158 {} |
1984 , const value_traits &v_traits = value_traits()) | 2163 , const value_traits &v_traits = value_traits()) |
1985 : Base(unique, b, e, cmp, v_traits) | 2164 : Base(unique, b, e, cmp, v_traits) |
1986 {} | 2165 {} |
1987 | 2166 |
1988 bstree(BOOST_RV_REF(bstree) x) | 2167 bstree(BOOST_RV_REF(bstree) x) |
1989 : Base(::boost::move(static_cast<Base&>(x))) | 2168 : Base(BOOST_MOVE_BASE(Base, x)) |
1990 {} | 2169 {} |
1991 | 2170 |
1992 bstree& operator=(BOOST_RV_REF(bstree) x) | 2171 bstree& operator=(BOOST_RV_REF(bstree) x) |
1993 { return static_cast<bstree &>(this->Base::operator=(::boost::move(static_cast<Base&>(x)))); } | 2172 { return static_cast<bstree &>(this->Base::operator=(BOOST_MOVE_BASE(Base, x))); } |
1994 | 2173 |
1995 static bstree &container_from_end_iterator(iterator end_iterator) | 2174 static bstree &container_from_end_iterator(iterator end_iterator) |
1996 { return static_cast<bstree &>(Base::container_from_end_iterator(end_iterator)); } | 2175 { return static_cast<bstree &>(Base::container_from_end_iterator(end_iterator)); } |
1997 | 2176 |
1998 static const bstree &container_from_end_iterator(const_iterator end_iterator) | 2177 static const bstree &container_from_end_iterator(const_iterator end_iterator) |