1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/epoc32/include/stdapis/boost/multi_index/sequenced_index.hpp Tue Mar 16 16:12:26 2010 +0000
1.3 @@ -0,0 +1,839 @@
1.4 +/* Copyright 2003-2007 Joaquín M López Muñoz.
1.5 + * Distributed under the Boost Software License, Version 1.0.
1.6 + * (See accompanying file LICENSE_1_0.txt or copy at
1.7 + * http://www.boost.org/LICENSE_1_0.txt)
1.8 + *
1.9 + * See http://www.boost.org/libs/multi_index for library home page.
1.10 + */
1.11 +
1.12 +#ifndef BOOST_MULTI_INDEX_SEQUENCED_INDEX_HPP
1.13 +#define BOOST_MULTI_INDEX_SEQUENCED_INDEX_HPP
1.14 +
1.15 +#if defined(_MSC_VER)&&(_MSC_VER>=1200)
1.16 +#pragma once
1.17 +#endif
1.18 +
1.19 +#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
1.20 +#include <boost/call_traits.hpp>
1.21 +#include <boost/detail/no_exceptions_support.hpp>
1.22 +#include <boost/detail/workaround.hpp>
1.23 +#include <boost/iterator/reverse_iterator.hpp>
1.24 +#include <boost/mpl/push_front.hpp>
1.25 +#include <boost/multi_index/detail/access_specifier.hpp>
1.26 +#include <boost/multi_index/detail/bidir_node_iterator.hpp>
1.27 +#include <boost/multi_index/detail/index_node_base.hpp>
1.28 +#include <boost/multi_index/detail/safe_ctr_proxy.hpp>
1.29 +#include <boost/multi_index/detail/safe_mode.hpp>
1.30 +#include <boost/multi_index/detail/scope_guard.hpp>
1.31 +#include <boost/multi_index/detail/seq_index_node.hpp>
1.32 +#include <boost/multi_index/detail/seq_index_ops.hpp>
1.33 +#include <boost/multi_index/sequenced_index_fwd.hpp>
1.34 +#include <boost/tuple/tuple.hpp>
1.35 +#include <cstddef>
1.36 +#include <functional>
1.37 +#include <utility>
1.38 +
1.39 +#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
1.40 +#include <boost/bind.hpp>
1.41 +#endif
1.42 +
1.43 +#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)
1.44 +#define BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT \
1.45 + detail::scope_guard BOOST_JOIN(check_invariant_,__LINE__)= \
1.46 + detail::make_obj_guard(*this,&sequenced_index::check_invariant_); \
1.47 + BOOST_JOIN(check_invariant_,__LINE__).touch();
1.48 +#else
1.49 +#define BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT
1.50 +#endif
1.51 +
1.52 +namespace boost{
1.53 +
1.54 +namespace multi_index{
1.55 +
1.56 +namespace detail{
1.57 +
1.58 +/* sequenced_index adds a layer of sequenced indexing to a given Super */
1.59 +
1.60 +template<typename SuperMeta,typename TagList>
1.61 +class sequenced_index:
1.62 + BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS SuperMeta::type
1.63 +
1.64 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.65 +#if BOOST_WORKAROUND(BOOST_MSVC,<1300)
1.66 + ,public safe_ctr_proxy_impl<
1.67 + bidir_node_iterator<
1.68 + sequenced_index_node<typename SuperMeta::type::node_type> >,
1.69 + sequenced_index<SuperMeta,TagList> >
1.70 +#else
1.71 + ,public safe_mode::safe_container<
1.72 + sequenced_index<SuperMeta,TagList> >
1.73 +#endif
1.74 +#endif
1.75 +
1.76 +{
1.77 +#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
1.78 + BOOST_WORKAROUND(__MWERKS__,<=0x3003)
1.79 +/* The "ISO C++ Template Parser" option in CW8.3 has a problem with the
1.80 + * lifetime of const references bound to temporaries --precisely what
1.81 + * scopeguards are.
1.82 + */
1.83 +
1.84 +#pragma parse_mfunc_templ off
1.85 +#endif
1.86 +
1.87 + typedef typename SuperMeta::type super;
1.88 +
1.89 +protected:
1.90 + typedef sequenced_index_node<
1.91 + typename super::node_type> node_type;
1.92 +
1.93 +public:
1.94 + /* types */
1.95 +
1.96 + typedef typename node_type::value_type value_type;
1.97 + typedef tuples::null_type ctor_args;
1.98 + typedef typename super::final_allocator_type allocator_type;
1.99 + typedef typename allocator_type::reference reference;
1.100 + typedef typename allocator_type::const_reference const_reference;
1.101 +
1.102 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.103 +#if BOOST_WORKAROUND(BOOST_MSVC,<1300)
1.104 + typedef safe_mode::safe_iterator<
1.105 + bidir_node_iterator<node_type>,
1.106 + safe_ctr_proxy<
1.107 + bidir_node_iterator<node_type> > > iterator;
1.108 +#else
1.109 + typedef safe_mode::safe_iterator<
1.110 + bidir_node_iterator<node_type>,
1.111 + sequenced_index> iterator;
1.112 +#endif
1.113 +#else
1.114 + typedef bidir_node_iterator<node_type> iterator;
1.115 +#endif
1.116 +
1.117 + typedef iterator const_iterator;
1.118 +
1.119 + typedef std::size_t size_type;
1.120 + typedef std::ptrdiff_t difference_type;
1.121 + typedef typename allocator_type::pointer pointer;
1.122 + typedef typename allocator_type::const_pointer const_pointer;
1.123 + typedef typename
1.124 + boost::reverse_iterator<iterator> reverse_iterator;
1.125 + typedef typename
1.126 + boost::reverse_iterator<const_iterator> const_reverse_iterator;
1.127 + typedef TagList tag_list;
1.128 +
1.129 +protected:
1.130 + typedef typename super::final_node_type final_node_type;
1.131 + typedef tuples::cons<
1.132 + ctor_args,
1.133 + typename super::ctor_args_list> ctor_args_list;
1.134 + typedef typename mpl::push_front<
1.135 + typename super::index_type_list,
1.136 + sequenced_index>::type index_type_list;
1.137 + typedef typename mpl::push_front<
1.138 + typename super::iterator_type_list,
1.139 + iterator>::type iterator_type_list;
1.140 + typedef typename mpl::push_front<
1.141 + typename super::const_iterator_type_list,
1.142 + const_iterator>::type const_iterator_type_list;
1.143 + typedef typename super::copy_map_type copy_map_type;
1.144 +
1.145 +#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
1.146 + typedef typename super::index_saver_type index_saver_type;
1.147 + typedef typename super::index_loader_type index_loader_type;
1.148 +#endif
1.149 +
1.150 +private:
1.151 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.152 +#if BOOST_WORKAROUND(BOOST_MSVC,<1300)
1.153 + typedef safe_ctr_proxy_impl<
1.154 + bidir_node_iterator<node_type>,
1.155 + sequenced_index> safe_super;
1.156 +#else
1.157 + typedef safe_mode::safe_container<
1.158 + sequenced_index> safe_super;
1.159 +#endif
1.160 +#endif
1.161 +
1.162 + typedef typename call_traits<value_type>::param_type value_param_type;
1.163 +
1.164 +public:
1.165 +
1.166 + /* construct/copy/destroy
1.167 + * Default and copy ctors are in the protected section as indices are
1.168 + * not supposed to be created on their own. No range ctor either.
1.169 + */
1.170 +
1.171 + sequenced_index<SuperMeta,TagList>& operator=(
1.172 + const sequenced_index<SuperMeta,TagList>& x)
1.173 + {
1.174 + this->final()=x.final();
1.175 + return *this;
1.176 + }
1.177 +
1.178 + template <class InputIterator>
1.179 + void assign(InputIterator first,InputIterator last)
1.180 + {
1.181 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.182 + clear();
1.183 + for(;first!=last;++first)push_back(*first);
1.184 + }
1.185 +
1.186 + void assign(size_type n,value_param_type value)
1.187 + {
1.188 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.189 + clear();
1.190 + for(size_type i=0;i<n;++i)push_back(value);
1.191 + }
1.192 +
1.193 + allocator_type get_allocator()const
1.194 + {
1.195 + return this->final().get_allocator();
1.196 + }
1.197 +
1.198 + /* iterators */
1.199 +
1.200 + iterator begin()
1.201 + {return make_iterator(node_type::from_impl(header()->next()));}
1.202 + const_iterator begin()const
1.203 + {return make_iterator(node_type::from_impl(header()->next()));}
1.204 + iterator end(){return make_iterator(header());}
1.205 + const_iterator end()const{return make_iterator(header());}
1.206 + reverse_iterator rbegin(){return make_reverse_iterator(end());}
1.207 + const_reverse_iterator rbegin()const{return make_reverse_iterator(end());}
1.208 + reverse_iterator rend(){return make_reverse_iterator(begin());}
1.209 + const_reverse_iterator rend()const{return make_reverse_iterator(begin());}
1.210 +
1.211 + /* capacity */
1.212 +
1.213 + bool empty()const{return this->final_empty_();}
1.214 + size_type size()const{return this->final_size_();}
1.215 + size_type max_size()const{return this->final_max_size_();}
1.216 +
1.217 + void resize(size_type n,value_param_type x=value_type())
1.218 + {
1.219 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.220 + if(n>size())insert(end(),n-size(),x);
1.221 + else if(n<size()){
1.222 + iterator it=begin();
1.223 + std::advance(it,n);
1.224 + erase(it,end());
1.225 + }
1.226 + }
1.227 +
1.228 + /* access: no non-const versions provided as sequenced_index
1.229 + * handles const elements.
1.230 + */
1.231 +
1.232 + const_reference front()const{return *begin();}
1.233 + const_reference back()const{return *--end();}
1.234 +
1.235 + /* modifiers */
1.236 +
1.237 + std::pair<iterator,bool> push_front(value_param_type x)
1.238 + {return insert(begin(),x);}
1.239 + void pop_front(){erase(begin());}
1.240 + std::pair<iterator,bool> push_back(value_param_type x)
1.241 + {return insert(end(),x);}
1.242 + void pop_back(){erase(--end());}
1.243 +
1.244 + std::pair<iterator,bool> insert(iterator position,value_param_type x)
1.245 + {
1.246 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.247 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.248 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.249 + std::pair<final_node_type*,bool> p=this->final_insert_(x);
1.250 + if(p.second&&position.get_node()!=header()){
1.251 + relink(position.get_node(),p.first);
1.252 + }
1.253 + return std::pair<iterator,bool>(make_iterator(p.first),p.second);
1.254 + }
1.255 +
1.256 + void insert(iterator position,size_type n,value_param_type x)
1.257 + {
1.258 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.259 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.260 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.261 + for(size_type i=0;i<n;++i)insert(position,x);
1.262 + }
1.263 +
1.264 + template<typename InputIterator>
1.265 + void insert(iterator position,InputIterator first,InputIterator last)
1.266 + {
1.267 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.268 + for(;first!=last;++first)insert(position,*first);
1.269 + }
1.270 +
1.271 + iterator erase(iterator position)
1.272 + {
1.273 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.274 + BOOST_MULTI_INDEX_CHECK_DEREFERENCEABLE_ITERATOR(position);
1.275 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.276 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.277 + this->final_erase_(static_cast<final_node_type*>(position++.get_node()));
1.278 + return position;
1.279 + }
1.280 +
1.281 + iterator erase(iterator first,iterator last)
1.282 + {
1.283 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(first);
1.284 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(last);
1.285 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(first,*this);
1.286 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(last,*this);
1.287 + BOOST_MULTI_INDEX_CHECK_VALID_RANGE(first,last);
1.288 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.289 + while(first!=last){
1.290 + first=erase(first);
1.291 + }
1.292 + return first;
1.293 + }
1.294 +
1.295 + bool replace(iterator position,value_param_type x)
1.296 + {
1.297 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.298 + BOOST_MULTI_INDEX_CHECK_DEREFERENCEABLE_ITERATOR(position);
1.299 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.300 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.301 + return this->final_replace_(
1.302 + x,static_cast<final_node_type*>(position.get_node()));
1.303 + }
1.304 +
1.305 + template<typename Modifier>
1.306 + bool modify(iterator position,Modifier mod)
1.307 + {
1.308 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.309 + BOOST_MULTI_INDEX_CHECK_DEREFERENCEABLE_ITERATOR(position);
1.310 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.311 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.312 +
1.313 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.314 + /* MSVC++ 6.0 optimizer on safe mode code chokes if this
1.315 + * this is not added. Left it for all compilers as it does no
1.316 + * harm.
1.317 + */
1.318 +
1.319 + position.detach();
1.320 +#endif
1.321 +
1.322 + return this->final_modify_(
1.323 + mod,static_cast<final_node_type*>(position.get_node()));
1.324 + }
1.325 +
1.326 + void swap(sequenced_index<SuperMeta,TagList>& x)
1.327 + {
1.328 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.329 + this->final_swap_(x.final());
1.330 + }
1.331 +
1.332 + void clear()
1.333 + {
1.334 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.335 + this->final_clear_();
1.336 + }
1.337 +
1.338 + /* list operations */
1.339 +
1.340 + void splice(iterator position,sequenced_index<SuperMeta,TagList>& x)
1.341 + {
1.342 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.343 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.344 + BOOST_MULTI_INDEX_CHECK_DIFFERENT_CONTAINER(*this,x);
1.345 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.346 + iterator first=x.begin(),last=x.end();
1.347 + while(first!=last){
1.348 + if(insert(position,*first).second)first=x.erase(first);
1.349 + else ++first;
1.350 + }
1.351 + }
1.352 +
1.353 + void splice(iterator position,sequenced_index<SuperMeta,TagList>& x,iterator i)
1.354 + {
1.355 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.356 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.357 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(i);
1.358 + BOOST_MULTI_INDEX_CHECK_DEREFERENCEABLE_ITERATOR(i);
1.359 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(i,x);
1.360 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.361 + if(&x==this){
1.362 + if(position!=i)relink(position.get_node(),i.get_node());
1.363 + }
1.364 + else{
1.365 + if(insert(position,*i).second){
1.366 +
1.367 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.368 + /* MSVC++ 6.0 optimizer has a hard time with safe mode, and the following
1.369 + * workaround is needed. Left it for all compilers as it does no
1.370 + * harm.
1.371 + */
1.372 + i.detach();
1.373 + x.erase(x.make_iterator(i.get_node()));
1.374 +#else
1.375 + x.erase(i);
1.376 +#endif
1.377 +
1.378 + }
1.379 + }
1.380 + }
1.381 +
1.382 + void splice(
1.383 + iterator position,sequenced_index<SuperMeta,TagList>& x,
1.384 + iterator first,iterator last)
1.385 + {
1.386 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.387 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.388 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(first);
1.389 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(last);
1.390 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(first,x);
1.391 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(last,x);
1.392 + BOOST_MULTI_INDEX_CHECK_VALID_RANGE(first,last);
1.393 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.394 + if(&x==this){
1.395 + BOOST_MULTI_INDEX_CHECK_OUTSIDE_RANGE(position,first,last);
1.396 + if(position!=last)relink(
1.397 + position.get_node(),first.get_node(),last.get_node());
1.398 + }
1.399 + else{
1.400 + while(first!=last){
1.401 + if(insert(position,*first).second)first=x.erase(first);
1.402 + else ++first;
1.403 + }
1.404 + }
1.405 + }
1.406 +
1.407 + void remove(value_param_type value)
1.408 + {
1.409 + sequenced_index_remove(
1.410 + *this,std::bind2nd(std::equal_to<value_type>(),value));
1.411 + }
1.412 +
1.413 + template<typename Predicate>
1.414 + void remove_if(Predicate pred)
1.415 + {
1.416 + sequenced_index_remove(*this,pred);
1.417 + }
1.418 +
1.419 + void unique()
1.420 + {
1.421 + sequenced_index_unique(*this,std::equal_to<value_type>());
1.422 + }
1.423 +
1.424 + template <class BinaryPredicate>
1.425 + void unique(BinaryPredicate binary_pred)
1.426 + {
1.427 + sequenced_index_unique(*this,binary_pred);
1.428 + }
1.429 +
1.430 + void merge(sequenced_index<SuperMeta,TagList>& x)
1.431 + {
1.432 + sequenced_index_merge(*this,x,std::less<value_type>());
1.433 + }
1.434 +
1.435 + template <typename Compare>
1.436 + void merge(sequenced_index<SuperMeta,TagList>& x,Compare comp)
1.437 + {
1.438 + sequenced_index_merge(*this,x,comp);
1.439 + }
1.440 +
1.441 + void sort()
1.442 + {
1.443 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.444 + sequenced_index_sort(header(),std::less<value_type>());
1.445 + }
1.446 +
1.447 + template <typename Compare>
1.448 + void sort(Compare comp)
1.449 + {
1.450 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.451 + sequenced_index_sort(header(),comp);
1.452 + }
1.453 +
1.454 + void reverse()
1.455 + {
1.456 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.457 + sequenced_index_node_impl::reverse(header()->impl());
1.458 + }
1.459 +
1.460 + /* rearrange operations */
1.461 +
1.462 + void relocate(iterator position,iterator i)
1.463 + {
1.464 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.465 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.466 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(i);
1.467 + BOOST_MULTI_INDEX_CHECK_DEREFERENCEABLE_ITERATOR(i);
1.468 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(i,*this);
1.469 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.470 + if(position!=i)relink(position.get_node(),i.get_node());
1.471 + }
1.472 +
1.473 + void relocate(iterator position,iterator first,iterator last)
1.474 + {
1.475 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(position);
1.476 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(position,*this);
1.477 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(first);
1.478 + BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(last);
1.479 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(first,*this);
1.480 + BOOST_MULTI_INDEX_CHECK_IS_OWNER(last,*this);
1.481 + BOOST_MULTI_INDEX_CHECK_VALID_RANGE(first,last);
1.482 + BOOST_MULTI_INDEX_CHECK_OUTSIDE_RANGE(position,first,last);
1.483 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.484 + if(position!=last)relink(
1.485 + position.get_node(),first.get_node(),last.get_node());
1.486 + }
1.487 +
1.488 + template<typename InputIterator>
1.489 + void rearrange(InputIterator first)
1.490 + {
1.491 + BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT;
1.492 + node_type* pos=header();
1.493 + for(size_type s=size();s--;){
1.494 + const value_type& v=*first++;
1.495 + relink(pos,node_from_value<node_type>(&v));
1.496 + }
1.497 + }
1.498 +
1.499 +BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
1.500 + sequenced_index(const ctor_args_list& args_list,const allocator_type& al):
1.501 + super(args_list.get_tail(),al)
1.502 + {
1.503 + empty_initialize();
1.504 + }
1.505 +
1.506 + sequenced_index(const sequenced_index<SuperMeta,TagList>& x):
1.507 + super(x)
1.508 +
1.509 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.510 + ,safe_super()
1.511 +#endif
1.512 +
1.513 + {
1.514 + /* The actual copying takes place in subsequent call to copy_().
1.515 + */
1.516 + }
1.517 +
1.518 + ~sequenced_index()
1.519 + {
1.520 + /* the container is guaranteed to be empty by now */
1.521 + }
1.522 +
1.523 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.524 + iterator make_iterator(node_type* node){return iterator(node,this);}
1.525 + const_iterator make_iterator(node_type* node)const
1.526 + {return const_iterator(node,const_cast<sequenced_index*>(this));}
1.527 +#else
1.528 + iterator make_iterator(node_type* node){return iterator(node);}
1.529 + const_iterator make_iterator(node_type* node)const
1.530 + {return const_iterator(node);}
1.531 +#endif
1.532 +
1.533 + void copy_(
1.534 + const sequenced_index<SuperMeta,TagList>& x,const copy_map_type& map)
1.535 + {
1.536 + node_type* org=x.header();
1.537 + node_type* cpy=header();
1.538 + do{
1.539 + node_type* next_org=node_type::from_impl(org->next());
1.540 + node_type* next_cpy=map.find(static_cast<final_node_type*>(next_org));
1.541 + cpy->next()=next_cpy->impl();
1.542 + next_cpy->prior()=cpy->impl();
1.543 + org=next_org;
1.544 + cpy=next_cpy;
1.545 + }while(org!=x.header());
1.546 +
1.547 + super::copy_(x,map);
1.548 + }
1.549 +
1.550 + node_type* insert_(value_param_type v,node_type* x)
1.551 + {
1.552 + node_type* res=static_cast<node_type*>(super::insert_(v,x));
1.553 + if(res==x)link(x);
1.554 + return res;
1.555 + }
1.556 +
1.557 + node_type* insert_(value_param_type v,node_type* position,node_type* x)
1.558 + {
1.559 + node_type* res=static_cast<node_type*>(super::insert_(v,position,x));
1.560 + if(res==x)link(x);
1.561 + return res;
1.562 + }
1.563 +
1.564 + void erase_(node_type* x)
1.565 + {
1.566 + unlink(x);
1.567 + super::erase_(x);
1.568 +
1.569 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.570 + detach_iterators(x);
1.571 +#endif
1.572 + }
1.573 +
1.574 + void delete_all_nodes_()
1.575 + {
1.576 + for(node_type* x=node_type::from_impl(header()->next());x!=header();){
1.577 + node_type* y=node_type::from_impl(x->next());
1.578 + this->final_delete_node_(static_cast<final_node_type*>(x));
1.579 + x=y;
1.580 + }
1.581 + }
1.582 +
1.583 + void clear_()
1.584 + {
1.585 + super::clear_();
1.586 + empty_initialize();
1.587 +
1.588 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.589 + safe_super::detach_dereferenceable_iterators();
1.590 +#endif
1.591 + }
1.592 +
1.593 + void swap_(sequenced_index<SuperMeta,TagList>& x)
1.594 + {
1.595 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.596 + safe_super::swap(x);
1.597 +#endif
1.598 +
1.599 + super::swap_(x);
1.600 + }
1.601 +
1.602 + bool replace_(value_param_type v,node_type* x)
1.603 + {
1.604 + return super::replace_(v,x);
1.605 + }
1.606 +
1.607 + bool modify_(node_type* x)
1.608 + {
1.609 + BOOST_TRY{
1.610 + if(!super::modify_(x)){
1.611 + unlink(x);
1.612 +
1.613 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.614 + detach_iterators(x);
1.615 +#endif
1.616 +
1.617 + return false;
1.618 + }
1.619 + else return true;
1.620 + }
1.621 + BOOST_CATCH(...){
1.622 + unlink(x);
1.623 +
1.624 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.625 + detach_iterators(x);
1.626 +#endif
1.627 +
1.628 + BOOST_RETHROW;
1.629 + }
1.630 + BOOST_CATCH_END
1.631 + }
1.632 +
1.633 +#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
1.634 + /* serialization */
1.635 +
1.636 + template<typename Archive>
1.637 + void save_(
1.638 + Archive& ar,const unsigned int version,const index_saver_type& sm)const
1.639 + {
1.640 + sm.save(begin(),end(),ar,version);
1.641 + super::save_(ar,version,sm);
1.642 + }
1.643 +
1.644 + template<typename Archive>
1.645 + void load_(
1.646 + Archive& ar,const unsigned int version,const index_loader_type& lm)
1.647 + {
1.648 + lm.load(
1.649 + ::boost::bind(&sequenced_index::rearranger,this,_1,_2),
1.650 + ar,version);
1.651 + super::load_(ar,version,lm);
1.652 + }
1.653 +#endif
1.654 +
1.655 +#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)
1.656 + /* invariant stuff */
1.657 +
1.658 + bool invariant_()const
1.659 + {
1.660 + if(size()==0||begin()==end()){
1.661 + if(size()!=0||begin()!=end()||
1.662 + header()->next()!=header()->impl()||
1.663 + header()->prior()!=header()->impl())return false;
1.664 + }
1.665 + else{
1.666 + size_type s=0;
1.667 + for(const_iterator it=begin(),it_end=end();it!=it_end;++it,++s){
1.668 + if(it.get_node()->next()->prior()!=it.get_node()->impl())return false;
1.669 + if(it.get_node()->prior()->next()!=it.get_node()->impl())return false;
1.670 + }
1.671 + if(s!=size())return false;
1.672 + }
1.673 +
1.674 + return super::invariant_();
1.675 + }
1.676 +
1.677 + /* This forwarding function eases things for the boost::mem_fn construct
1.678 + * in BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT. Actually,
1.679 + * final_check_invariant is already an inherited member function of index.
1.680 + */
1.681 + void check_invariant_()const{this->final_check_invariant_();}
1.682 +#endif
1.683 +
1.684 +private:
1.685 + node_type* header()const{return this->final_header();}
1.686 +
1.687 + void empty_initialize()
1.688 + {
1.689 + header()->prior()=header()->next()=header()->impl();
1.690 + }
1.691 +
1.692 + void link(node_type* x)
1.693 + {
1.694 + sequenced_index_node_impl::link(x->impl(),header()->impl());
1.695 + };
1.696 +
1.697 + static void unlink(node_type* x)
1.698 + {
1.699 + sequenced_index_node_impl::unlink(x->impl());
1.700 + }
1.701 +
1.702 + static void relink(node_type* position,node_type* x)
1.703 + {
1.704 + sequenced_index_node_impl::relink(position->impl(),x->impl());
1.705 + }
1.706 +
1.707 + static void relink(node_type* position,node_type* first,node_type* last)
1.708 + {
1.709 + sequenced_index_node_impl::relink(
1.710 + position->impl(),first->impl(),last->impl());
1.711 + }
1.712 +
1.713 +#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
1.714 + void rearranger(node_type* position,node_type *x)
1.715 + {
1.716 + if(!position)position=header();
1.717 + node_type::increment(position);
1.718 + if(position!=x)relink(position,x);
1.719 + }
1.720 +#endif
1.721 +
1.722 +#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
1.723 + void detach_iterators(node_type* x)
1.724 + {
1.725 + iterator it=make_iterator(x);
1.726 + safe_mode::detach_equivalent_iterators(it);
1.727 + }
1.728 +#endif
1.729 +
1.730 +#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
1.731 + BOOST_WORKAROUND(__MWERKS__,<=0x3003)
1.732 +#pragma parse_mfunc_templ reset
1.733 +#endif
1.734 +};
1.735 +
1.736 +/* comparison */
1.737 +
1.738 +template<
1.739 + typename SuperMeta1,typename TagList1,
1.740 + typename SuperMeta2,typename TagList2
1.741 +>
1.742 +bool operator==(
1.743 + const sequenced_index<SuperMeta1,TagList1>& x,
1.744 + const sequenced_index<SuperMeta2,TagList2>& y)
1.745 +{
1.746 + return x.size()==y.size()&&std::equal(x.begin(),x.end(),y.begin());
1.747 +}
1.748 +
1.749 +template<
1.750 + typename SuperMeta1,typename TagList1,
1.751 + typename SuperMeta2,typename TagList2
1.752 +>
1.753 +bool operator<(
1.754 + const sequenced_index<SuperMeta1,TagList1>& x,
1.755 + const sequenced_index<SuperMeta2,TagList2>& y)
1.756 +{
1.757 + return std::lexicographical_compare(x.begin(),x.end(),y.begin(),y.end());
1.758 +}
1.759 +
1.760 +template<
1.761 + typename SuperMeta1,typename TagList1,
1.762 + typename SuperMeta2,typename TagList2
1.763 +>
1.764 +bool operator!=(
1.765 + const sequenced_index<SuperMeta1,TagList1>& x,
1.766 + const sequenced_index<SuperMeta2,TagList2>& y)
1.767 +{
1.768 + return !(x==y);
1.769 +}
1.770 +
1.771 +template<
1.772 + typename SuperMeta1,typename TagList1,
1.773 + typename SuperMeta2,typename TagList2
1.774 +>
1.775 +bool operator>(
1.776 + const sequenced_index<SuperMeta1,TagList1>& x,
1.777 + const sequenced_index<SuperMeta2,TagList2>& y)
1.778 +{
1.779 + return y<x;
1.780 +}
1.781 +
1.782 +template<
1.783 + typename SuperMeta1,typename TagList1,
1.784 + typename SuperMeta2,typename TagList2
1.785 +>
1.786 +bool operator>=(
1.787 + const sequenced_index<SuperMeta1,TagList1>& x,
1.788 + const sequenced_index<SuperMeta2,TagList2>& y)
1.789 +{
1.790 + return !(x<y);
1.791 +}
1.792 +
1.793 +template<
1.794 + typename SuperMeta1,typename TagList1,
1.795 + typename SuperMeta2,typename TagList2
1.796 +>
1.797 +bool operator<=(
1.798 + const sequenced_index<SuperMeta1,TagList1>& x,
1.799 + const sequenced_index<SuperMeta2,TagList2>& y)
1.800 +{
1.801 + return !(x>y);
1.802 +}
1.803 +
1.804 +/* specialized algorithms */
1.805 +
1.806 +template<typename SuperMeta,typename TagList>
1.807 +void swap(
1.808 + sequenced_index<SuperMeta,TagList>& x,
1.809 + sequenced_index<SuperMeta,TagList>& y)
1.810 +{
1.811 + x.swap(y);
1.812 +}
1.813 +
1.814 +} /* namespace multi_index::detail */
1.815 +
1.816 +/* sequenced index specifier */
1.817 +
1.818 +template <typename TagList>
1.819 +struct sequenced
1.820 +{
1.821 + BOOST_STATIC_ASSERT(detail::is_tag<TagList>::value);
1.822 +
1.823 + template<typename Super>
1.824 + struct node_class
1.825 + {
1.826 + typedef detail::sequenced_index_node<Super> type;
1.827 + };
1.828 +
1.829 + template<typename SuperMeta>
1.830 + struct index_class
1.831 + {
1.832 + typedef detail::sequenced_index<SuperMeta,typename TagList::type> type;
1.833 + };
1.834 +};
1.835 +
1.836 +} /* namespace multi_index */
1.837 +
1.838 +} /* namespace boost */
1.839 +
1.840 +#undef BOOST_MULTI_INDEX_SEQ_INDEX_CHECK_INVARIANT
1.841 +
1.842 +#endif