]> git.proxmox.com Git - ceph.git/blame - ceph/src/boost/boost/geometry/index/detail/rtree/node/variant_dynamic.hpp
update sources to ceph Nautilus 14.2.1
[ceph.git] / ceph / src / boost / boost / geometry / index / detail / rtree / node / variant_dynamic.hpp
CommitLineData
7c673cae
FG
1// Boost.Geometry Index
2//
3// R-tree nodes based on Boost.Variant, storing dynamic-size containers
4//
11fdf7f2 5// Copyright (c) 2011-2018 Adam Wulkiewicz, Lodz, Poland.
7c673cae
FG
6//
7// Use, modification and distribution is subject to the Boost Software License,
8// Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
9// http://www.boost.org/LICENSE_1_0.txt)
10
11#ifndef BOOST_GEOMETRY_INDEX_DETAIL_RTREE_NODE_VARIANT_DYNAMIC_HPP
12#define BOOST_GEOMETRY_INDEX_DETAIL_RTREE_NODE_VARIANT_DYNAMIC_HPP
13
b32b8144
FG
14#include <boost/core/pointer_traits.hpp>
15
7c673cae
FG
16namespace boost { namespace geometry { namespace index {
17
18namespace detail { namespace rtree {
19
20// nodes default types
21
22template <typename Value, typename Parameters, typename Box, typename Allocators, typename Tag>
23struct variant_internal_node
24{
11fdf7f2
TL
25 typedef rtree::ptr_pair<Box, typename Allocators::node_pointer> element_type;
26 typedef typename boost::container::allocator_traits
7c673cae 27 <
11fdf7f2
TL
28 typename Allocators::node_allocator_type
29 >::template rebind_alloc<element_type> allocator_type;
30
31 typedef boost::container::vector<element_type, allocator_type> elements_type;
7c673cae
FG
32
33 template <typename Al>
34 inline variant_internal_node(Al const& al)
11fdf7f2 35 : elements(allocator_type(al))
7c673cae
FG
36 {}
37
38 elements_type elements;
39};
40
41template <typename Value, typename Parameters, typename Box, typename Allocators, typename Tag>
42struct variant_leaf
43{
11fdf7f2 44 typedef typename boost::container::allocator_traits
7c673cae 45 <
11fdf7f2
TL
46 typename Allocators::node_allocator_type
47 >::template rebind_alloc<Value> allocator_type;
48
49 typedef boost::container::vector<Value, allocator_type> elements_type;
50
51 template <typename Al>
7c673cae 52 inline variant_leaf(Al const& al)
11fdf7f2 53 : elements(allocator_type(al))
7c673cae
FG
54 {}
55
56 elements_type elements;
57};
58
59// nodes traits
60
61template <typename Value, typename Parameters, typename Box, typename Allocators>
62struct node<Value, Parameters, Box, Allocators, node_variant_dynamic_tag>
63{
64 typedef boost::variant<
65 variant_leaf<Value, Parameters, Box, Allocators, node_variant_dynamic_tag>,
66 variant_internal_node<Value, Parameters, Box, Allocators, node_variant_dynamic_tag>
67 > type;
68};
69
70template <typename Value, typename Parameters, typename Box, typename Allocators>
71struct internal_node<Value, Parameters, Box, Allocators, node_variant_dynamic_tag>
72{
73 typedef variant_internal_node<Value, Parameters, Box, Allocators, node_variant_dynamic_tag> type;
74};
75
76template <typename Value, typename Parameters, typename Box, typename Allocators>
77struct leaf<Value, Parameters, Box, Allocators, node_variant_dynamic_tag>
78{
79 typedef variant_leaf<Value, Parameters, Box, Allocators, node_variant_dynamic_tag> type;
80};
81
82// visitor traits
83
84template <typename Value, typename Parameters, typename Box, typename Allocators, bool IsVisitableConst>
85struct visitor<Value, Parameters, Box, Allocators, node_variant_dynamic_tag, IsVisitableConst>
86{
87 typedef static_visitor<> type;
88};
89
90// allocators
91
11fdf7f2
TL
92template <typename Allocator, typename Value, typename Parameters, typename Box, typename Tag>
93struct node_alloc
94{
95 typedef typename node
96 <
97 Value, Parameters, Box,
98 allocators<Allocator, Value, Parameters, Box, Tag>,
99 Tag
100 >::type node_type;
101
102 typedef typename boost::container::allocator_traits
103 <
104 Allocator
105 >::template rebind_alloc<node_type> type;
106
107 typedef boost::container::allocator_traits<type> traits;
108};
109
110
7c673cae
FG
111template <typename Allocator, typename Value, typename Parameters, typename Box>
112class allocators<Allocator, Value, Parameters, Box, node_variant_dynamic_tag>
11fdf7f2
TL
113 : public detail::rtree::node_alloc
114 <
115 Allocator, Value, Parameters, Box, node_variant_dynamic_tag
7c673cae 116 >::type
7c673cae 117{
11fdf7f2
TL
118 typedef detail::rtree::node_alloc
119 <
120 Allocator, Value, Parameters, Box, node_variant_dynamic_tag
121 > node_alloc;
7c673cae
FG
122
123public:
11fdf7f2
TL
124 typedef typename node_alloc::type node_allocator_type;
125 typedef typename node_alloc::traits::pointer node_pointer;
7c673cae 126
11fdf7f2
TL
127private:
128 typedef typename boost::container::allocator_traits
129 <
130 node_allocator_type // node_allocator_type for consistency with variant_leaf
131 >::template rebind_alloc<Value> value_allocator_type;
132 typedef boost::container::allocator_traits<value_allocator_type> value_allocator_traits;
133
7c673cae 134
11fdf7f2
TL
135public:
136 typedef Allocator allocator_type;
7c673cae 137
11fdf7f2
TL
138 typedef Value value_type;
139 typedef typename value_allocator_traits::reference reference;
140 typedef typename value_allocator_traits::const_reference const_reference;
141 typedef typename value_allocator_traits::size_type size_type;
142 typedef typename value_allocator_traits::difference_type difference_type;
143 typedef typename value_allocator_traits::pointer pointer;
144 typedef typename value_allocator_traits::const_pointer const_pointer;
7c673cae
FG
145
146 inline allocators()
147 : node_allocator_type()
148 {}
149
150 template <typename Alloc>
151 inline explicit allocators(Alloc const& alloc)
152 : node_allocator_type(alloc)
153 {}
154
155 inline allocators(BOOST_FWD_REF(allocators) a)
156 : node_allocator_type(boost::move(a.node_allocator()))
157 {}
158
159 inline allocators & operator=(BOOST_FWD_REF(allocators) a)
160 {
161 node_allocator() = boost::move(a.node_allocator());
162 return *this;
163 }
164
165#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
166 inline allocators & operator=(allocators const& a)
167 {
168 node_allocator() = a.node_allocator();
169 return *this;
170 }
171#endif
172
173 void swap(allocators & a)
174 {
175 boost::swap(node_allocator(), a.node_allocator());
176 }
177
178 bool operator==(allocators const& a) const { return node_allocator() == a.node_allocator(); }
179 template <typename Alloc>
180 bool operator==(Alloc const& a) const { return node_allocator() == node_allocator_type(a); }
181
182 Allocator allocator() const { return Allocator(node_allocator()); }
183
184 node_allocator_type & node_allocator() { return *this; }
185 node_allocator_type const& node_allocator() const { return *this; }
186};
187
188// create_node_variant
189
190template <typename VariantPtr, typename Node>
191struct create_variant_node
192{
193 template <typename AllocNode>
194 static inline VariantPtr apply(AllocNode & alloc_node)
195 {
196 typedef boost::container::allocator_traits<AllocNode> Al;
197 typedef typename Al::pointer P;
198
199 P p = Al::allocate(alloc_node, 1);
200
201 if ( 0 == p )
202 throw_runtime_error("boost::geometry::index::rtree node creation failed");
203
204 scoped_deallocator<AllocNode> deallocator(p, alloc_node);
205
11fdf7f2 206 Al::construct(alloc_node, boost::to_address(p), Node(alloc_node)); // implicit cast to Variant
7c673cae
FG
207
208 deallocator.release();
209 return p;
210 }
211};
212
213// destroy_node_variant
214
215template <typename Node>
216struct destroy_variant_node
217{
218 template <typename AllocNode, typename VariantPtr>
219 static inline void apply(AllocNode & alloc_node, VariantPtr n)
220 {
221 typedef boost::container::allocator_traits<AllocNode> Al;
222
223 Al::destroy(alloc_node, boost::addressof(*n));
224 Al::deallocate(alloc_node, n, 1);
225 }
226};
227
228// create_node
229
230template <typename Allocators, typename Value, typename Parameters, typename Box, typename Tag>
231struct create_node<
232 Allocators,
233 variant_internal_node<Value, Parameters, Box, Allocators, Tag>
234>
235{
236 static inline typename Allocators::node_pointer
237 apply(Allocators & allocators)
238 {
239 return create_variant_node<
240 typename Allocators::node_pointer,
241 variant_internal_node<Value, Parameters, Box, Allocators, Tag>
242 >::apply(allocators.node_allocator());
243 }
244};
245
246template <typename Allocators, typename Value, typename Parameters, typename Box, typename Tag>
247struct create_node<
248 Allocators,
249 variant_leaf<Value, Parameters, Box, Allocators, Tag>
250>
251{
252 static inline typename Allocators::node_pointer
253 apply(Allocators & allocators)
254 {
255 return create_variant_node<
256 typename Allocators::node_pointer,
257 variant_leaf<Value, Parameters, Box, Allocators, Tag>
258 >::apply(allocators.node_allocator());
259 }
260};
261
262// destroy_node
263
264template <typename Allocators, typename Value, typename Parameters, typename Box, typename Tag>
265struct destroy_node<
266 Allocators,
267 variant_internal_node<Value, Parameters, Box, Allocators, Tag>
268>
269{
270 static inline void apply(Allocators & allocators, typename Allocators::node_pointer n)
271 {
272 destroy_variant_node<
273 variant_internal_node<Value, Parameters, Box, Allocators, Tag>
274 >::apply(allocators.node_allocator(), n);
275 }
276};
277
278template <typename Allocators, typename Value, typename Parameters, typename Box, typename Tag>
279struct destroy_node<
280 Allocators,
281 variant_leaf<Value, Parameters, Box, Allocators, Tag>
282>
283{
284 static inline void apply(Allocators & allocators, typename Allocators::node_pointer n)
285 {
286 destroy_variant_node<
287 variant_leaf<Value, Parameters, Box, Allocators, Tag>
288 >::apply(allocators.node_allocator(), n);
289 }
290};
291
292}} // namespace detail::rtree
293
294}}} // namespace boost::geometry::index
295
296#endif // BOOST_GEOMETRY_INDEX_DETAIL_RTREE_NODE_VARIANT_DYNAMIC_HPP