396635d3c4d7f9be193ea7acbda2c909846d2b11
[senf.git] / boost / bimap / container_adaptor / sequence_container_adaptor.hpp
1 // Boost.Bimap
2 //
3 // Copyright (c) 2006-2007 Matias Capeletto
4 //
5 // Distributed under the Boost Software License, Version 1.0.
6 // (See accompanying file LICENSE_1_0.txt or copy at
7 // http://www.boost.org/LICENSE_1_0.txt)
8
9 /// \file container_adaptor/sequence_container_adaptor.hpp
10 /// \brief Container adaptor to build a type that is compliant to the concept of a weak associative container.
11
12 #ifndef BOOST_BIMAP_CONTAINER_ADAPTOR_SEQUENCE_CONTAINER_ADAPTOR_HPP
13 #define BOOST_BIMAP_CONTAINER_ADAPTOR_SEQUENCE_CONTAINER_ADAPTOR_HPP
14
15 #if defined(_MSC_VER) && (_MSC_VER>=1200)
16 #pragma once
17 #endif
18
19 #include <boost/config.hpp>
20
21 #include <utility>
22
23 #include <boost/mpl/if.hpp>
24 #include <boost/mpl/vector.hpp>
25 #include <boost/mpl/aux_/na.hpp>
26 #include <boost/bimap/container_adaptor/detail/identity_converters.hpp>
27 #include <boost/bimap/container_adaptor/container_adaptor.hpp>
28 #include <boost/call_traits.hpp>
29
30 namespace boost {
31 namespace bimaps {
32 namespace container_adaptor {
33
34 #ifndef BOOST_BIMAP_DOXYGEN_WILL_NOT_PROCESS_THE_FOLLOWING_LINES
35
36 template
37 <
38     class Base, class Iterator, class ConstIterator,
39     class ReverseIterator, class ConstReverseIterator,
40     class IteratorToBaseConverter, class IteratorFromBaseConverter,
41     class ReverseIteratorFromBaseConverter,
42     class ValueToBaseConverter, class ValueFromBaseConverter,
43     class FunctorsFromDerivedClasses
44 >
45 struct sequence_container_adaptor_base
46 {
47     typedef container_adaptor
48     <
49         Base, Iterator, ConstIterator,
50         IteratorToBaseConverter, IteratorFromBaseConverter,
51         ValueToBaseConverter, ValueFromBaseConverter,
52
53         BOOST_DEDUCED_TYPENAME mpl::push_front<
54
55             FunctorsFromDerivedClasses,
56
57             BOOST_DEDUCED_TYPENAME mpl::if_<
58                 ::boost::mpl::is_na<ReverseIteratorFromBaseConverter>,
59             // {
60                     detail::iterator_from_base_identity
61                     <
62                         BOOST_DEDUCED_TYPENAME Base::reverse_iterator, 
63                         ReverseIterator,
64                         BOOST_DEDUCED_TYPENAME Base::const_reverse_iterator,
65                         ConstReverseIterator
66                     >,
67             // }
68             // else
69             // {
70                     ReverseIteratorFromBaseConverter
71             // }
72
73             >::type
74
75         >::type
76
77     > type;
78 };
79
80 #endif // BOOST_BIMAP_DOXYGEN_WILL_NOT_PROCESS_THE_FOLLOWING_LINES
81
82 /// \brief Container adaptor to build a type that is compliant to the concept of a sequence container.
83
84 template
85 <
86     class Base,
87
88     class Iterator,
89     class ConstIterator,
90
91     class ReverseIterator,
92     class ConstReverseIterator,
93
94     class IteratorToBaseConverter           = ::boost::mpl::na,
95     class IteratorFromBaseConverter         = ::boost::mpl::na,
96     class ReverseIteratorFromBaseConverter  = ::boost::mpl::na,
97     class ValueToBaseConverter              = ::boost::mpl::na,
98     class ValueFromBaseConverter            = ::boost::mpl::na,
99
100     class FunctorsFromDerivedClasses = mpl::vector<>
101 >
102 class sequence_container_adaptor :
103
104     public sequence_container_adaptor_base
105     <
106         Base, Iterator, ConstIterator,
107         ReverseIterator, ConstReverseIterator,
108         IteratorToBaseConverter, IteratorFromBaseConverter,
109         ReverseIteratorFromBaseConverter,
110         ValueToBaseConverter, ValueFromBaseConverter,
111         FunctorsFromDerivedClasses
112
113     >::type,
114
115     ::boost::totally_ordered
116     <
117         sequence_container_adaptor
118         <
119             Base, Iterator, ConstIterator,
120             ReverseIterator, ConstReverseIterator,
121             IteratorToBaseConverter, IteratorFromBaseConverter,
122             ReverseIteratorFromBaseConverter,
123             ValueToBaseConverter, ValueFromBaseConverter,
124             FunctorsFromDerivedClasses
125         >
126     >
127 {
128     typedef BOOST_DEDUCED_TYPENAME sequence_container_adaptor_base
129     <
130         Base, Iterator, ConstIterator,
131         ReverseIterator, ConstReverseIterator,
132         IteratorToBaseConverter, IteratorFromBaseConverter,
133         ReverseIteratorFromBaseConverter,
134         ValueToBaseConverter, ValueFromBaseConverter,
135         FunctorsFromDerivedClasses
136
137     >::type base_;
138
139     // MetaData -------------------------------------------------------------
140
141     public:
142
143     typedef ReverseIterator      reverse_iterator;
144     typedef ConstReverseIterator const_reverse_iterator;
145
146     protected:
147
148     typedef BOOST_DEDUCED_TYPENAME mpl::if_<
149         ::boost::mpl::is_na<ReverseIteratorFromBaseConverter>,
150         // {
151                 detail::iterator_from_base_identity
152                 <
153                     BOOST_DEDUCED_TYPENAME Base::reverse_iterator,
154                     reverse_iterator,
155                     BOOST_DEDUCED_TYPENAME Base::const_reverse_iterator,
156                     const_reverse_iterator
157                 >,
158         // }
159         // else
160         // {
161                 ReverseIteratorFromBaseConverter
162         // }
163
164         >::type reverse_iterator_from_base;
165
166
167     // Access -----------------------------------------------------------------
168
169     public:
170
171     explicit sequence_container_adaptor(Base & c)
172         : base_(c) {}
173
174     protected:
175
176
177     typedef sequence_container_adaptor sequence_container_adaptor_;
178
179     // Interface --------------------------------------------------------------
180
181     public:
182
183     reverse_iterator rbegin()
184     {
185         return this->template functor<
186             reverse_iterator_from_base
187         >()                            ( this->base().rbegin() );
188
189     }
190
191     reverse_iterator rend()
192     {
193         return this->template functor<
194             reverse_iterator_from_base
195         >()                            ( this->base().rend() );
196     }
197
198     const_reverse_iterator rbegin() const
199     {
200         return this->template functor<
201             reverse_iterator_from_base
202         >()                            ( this->base().rbegin() );
203     }
204
205     const_reverse_iterator rend() const
206     {
207         return this->template functor<
208             reverse_iterator_from_base
209         >()                            ( this->base().rend() );
210     }
211
212     void resize(BOOST_DEDUCED_TYPENAME base_::size_type n,
213                 BOOST_DEDUCED_TYPENAME ::boost::call_traits<
214                     BOOST_DEDUCED_TYPENAME base_::value_type >::param_type x =
215                         BOOST_DEDUCED_TYPENAME base_::value_type())
216     {
217         this->base().resize(n,
218             this->template functor<BOOST_DEDUCED_TYPENAME base_::value_to_base>()(x)
219         );
220     }
221
222     BOOST_DEDUCED_TYPENAME base_::reference front()
223     {
224         return this->template functor<
225             BOOST_DEDUCED_TYPENAME base_::value_from_base>()
226         (
227             this->base().front()
228         );
229     }
230
231     BOOST_DEDUCED_TYPENAME base_::reference back()
232     {
233         return this->template functor<
234             BOOST_DEDUCED_TYPENAME base_::value_from_base>()
235         (
236             this->base().back()
237         );
238     }
239
240     BOOST_DEDUCED_TYPENAME base_::const_reference front() const
241     {
242         return this->template functor<
243             BOOST_DEDUCED_TYPENAME base_::value_from_base>()
244         (
245             this->base().front()
246         );
247     }
248
249     BOOST_DEDUCED_TYPENAME base_::const_reference back() const
250     {
251         return this->template functor<
252             BOOST_DEDUCED_TYPENAME base_::value_from_base>()
253         (
254             this->base().back()
255         );
256     }
257
258     void push_front(
259         BOOST_DEDUCED_TYPENAME ::boost::call_traits<
260             BOOST_DEDUCED_TYPENAME base_::value_type >::param_type x)
261     {
262         this->base().push_front(
263             this->template functor<BOOST_DEDUCED_TYPENAME base_::value_to_base>()(x));
264     }
265
266     void pop_front()
267     {
268         this->base().pop_front();
269     }
270
271     void push_back(
272         BOOST_DEDUCED_TYPENAME ::boost::call_traits< 
273             BOOST_DEDUCED_TYPENAME base_::value_type >::param_type x)
274     {
275         this->base().push_back(
276             this->template functor<BOOST_DEDUCED_TYPENAME base_::value_to_base>()(x));
277     }
278
279     void pop_back()
280     {
281         this->base().pop_back();
282     }
283
284     std::pair<BOOST_DEDUCED_TYPENAME base_::iterator,bool>
285     insert(BOOST_DEDUCED_TYPENAME base_::iterator position,
286            BOOST_DEDUCED_TYPENAME ::boost::call_traits< 
287                 BOOST_DEDUCED_TYPENAME base_::value_type >::param_type x)
288     {
289         std::pair< BOOST_DEDUCED_TYPENAME Base::iterator, bool > r(
290             this->base().insert(
291                 this->template functor<
292                     BOOST_DEDUCED_TYPENAME base_::iterator_to_base>()(position),
293                 this->template functor<
294                     BOOST_DEDUCED_TYPENAME base_::value_to_base   >()(x)
295             )
296         );
297
298         return std::pair<BOOST_DEDUCED_TYPENAME base_::iterator, bool>(
299             this->template functor<
300                 BOOST_DEDUCED_TYPENAME base_::iterator_from_base>()(r.first),
301             r.second
302         );
303     }
304
305     void insert(BOOST_DEDUCED_TYPENAME base_::iterator position,
306                 BOOST_DEDUCED_TYPENAME base_::size_type m,
307                 BOOST_DEDUCED_TYPENAME ::boost::call_traits<
308                     BOOST_DEDUCED_TYPENAME base_::value_type >::param_type x)
309     {
310         this->base().insert(
311             this->template functor<
312                 BOOST_DEDUCED_TYPENAME base_::iterator_to_base>()(position),
313             m,
314             this->template functor<BOOST_DEDUCED_TYPENAME base_::value_to_base   >()(x)
315         );
316     }
317
318     template< class InputIterator >
319     void insert(BOOST_DEDUCED_TYPENAME base_::iterator position,
320                 InputIterator first, InputIterator last)
321     {
322         // This is the same problem found in the insert function 
323         // of container_adaptor
324         // For now, do the simple thing. This can be optimized
325
326         for( ; first != last ; ++first )
327         {
328             this->base().insert(
329                 this->template functor<
330                     BOOST_DEDUCED_TYPENAME base_::iterator_to_base>()( position ),
331                 this->template functor<
332                     BOOST_DEDUCED_TYPENAME base_::value_to_base   >()( *first )
333             );
334         }
335     }
336
337     // Totally ordered implementation
338
339     bool operator==(const sequence_container_adaptor & c) const
340     {
341         return ( this->base() == c.base() );
342     }
343
344     bool operator<(const sequence_container_adaptor & c) const
345     {
346         return ( this->base() < c.base() );
347     }
348 };
349
350 } // namespace container_adaptor
351 } // namespace bimaps
352 } // namespace boost
353
354
355 #endif // BOOST_BIMAP_CONTAINER_ADAPTOR_SEQUENCE_CONTAINER_ADAPTOR_HPP