Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-07-15 08:29:45

0001 //////////////////////////////////////////////////////////////////////////////
0002 //
0003 // (C) Copyright Ion Gaztanaga 2004-2015. Distributed under the Boost
0004 // Software License, Version 1.0. (See accompanying file
0005 // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
0006 //
0007 // See http://www.boost.org/libs/container for documentation.
0008 //
0009 //////////////////////////////////////////////////////////////////////////////
0010 
0011 #ifndef BOOST_CONTAINER_SLIST_HPP
0012 #define BOOST_CONTAINER_SLIST_HPP
0013 
0014 #ifndef BOOST_CONFIG_HPP
0015 #  include <boost/config.hpp>
0016 #endif
0017 
0018 #if defined(BOOST_HAS_PRAGMA_ONCE)
0019 #  pragma once
0020 #endif
0021 
0022 #include <boost/container/detail/config_begin.hpp>
0023 #include <boost/container/detail/workaround.hpp>
0024 
0025 // container
0026 #include <boost/container/container_fwd.hpp>
0027 #include <boost/container/new_allocator.hpp> //new_allocator
0028 #include <boost/container/throw_exception.hpp>
0029 // container/detail
0030 #include <boost/container/detail/algorithm.hpp> //algo_equal(), algo_lexicographical_compare
0031 #include <boost/container/detail/compare_functors.hpp>
0032 #include <boost/container/detail/iterator.hpp>
0033 #include <boost/container/detail/iterators.hpp>
0034 #include <boost/container/detail/mpl.hpp>
0035 #include <boost/container/detail/node_alloc_holder.hpp>
0036 #include <boost/container/detail/type_traits.hpp>
0037 #include <boost/container/detail/value_functors.hpp>
0038 // intrusive
0039 #include <boost/intrusive/pointer_traits.hpp>
0040 #include <boost/intrusive/slist.hpp>
0041 // move
0042 #include <boost/move/iterator.hpp>
0043 #include <boost/move/traits.hpp>
0044 #include <boost/move/utility_core.hpp>
0045 // move/detail
0046 #if defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
0047 #include <boost/move/detail/fwd_macros.hpp>
0048 #endif
0049 #include <boost/move/detail/move_helpers.hpp>
0050 
0051 // std
0052 #if !defined(BOOST_NO_CXX11_HDR_INITIALIZER_LIST)
0053 #include <initializer_list>
0054 #endif
0055 
0056 namespace boost {
0057 namespace container {
0058 
0059 #ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
0060 
0061 template <class T, class Allocator>
0062 class slist;
0063 
0064 namespace dtl {
0065 
0066 template<class VoidPointer>
0067 struct slist_hook
0068 {
0069    typedef typename dtl::bi::make_slist_base_hook
0070       <dtl::bi::void_pointer<VoidPointer>, dtl::bi::link_mode<dtl::bi::normal_link> >::type type;
0071 };
0072 
0073 template <class T, class VoidPointer>
0074 struct iiterator_node_value_type< base_node<T, slist_hook<VoidPointer> > >
0075 {
0076   typedef T type;
0077 };
0078 
0079 template<class Allocator>
0080 struct intrusive_slist_type
0081 {
0082    typedef boost::container::allocator_traits<Allocator>      allocator_traits_type;
0083    typedef typename allocator_traits_type::value_type value_type;
0084    typedef typename boost::intrusive::pointer_traits
0085       <typename allocator_traits_type::pointer>::template
0086          rebind_pointer<void>::type
0087             void_pointer;
0088    typedef base_node<value_type, slist_hook<void_pointer> > node_type;
0089 
0090    typedef typename dtl::bi::make_slist
0091       <node_type
0092       ,dtl::bi::base_hook<typename slist_hook<void_pointer>::type>
0093       ,dtl::bi::constant_time_size<true>
0094       , dtl::bi::size_type
0095          <typename allocator_traits_type::size_type>
0096       >::type                                   container_type;
0097    typedef container_type                       type ;
0098 };
0099 
0100 }  //namespace dtl {
0101 
0102 #endif   //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
0103 
0104 //! An slist is a singly linked list: a list where each element is linked to the next
0105 //! element, but not to the previous element. That is, it is a Sequence that
0106 //! supports forward but not backward traversal, and (amortized) constant time
0107 //! insertion and removal of elements. Slists, like lists, have the important
0108 //! property that insertion and splicing do not invalidate iterators to list elements,
0109 //! and that even removal invalidates only the iterators that point to the elements
0110 //! that are removed. The ordering of iterators may be changed (that is,
0111 //! slist<T>::iterator might have a different predecessor or successor after a list
0112 //! operation than it did before), but the iterators themselves will not be invalidated
0113 //! or made to point to different elements unless that invalidation or mutation is explicit.
0114 //!
0115 //! The main difference between slist and list is that list's iterators are bidirectional
0116 //! iterators, while slist's iterators are forward iterators. This means that slist is
0117 //! less versatile than list; frequently, however, bidirectional iterators are
0118 //! unnecessary. You should usually use slist unless you actually need the extra
0119 //! functionality of list, because singly linked lists are smaller and faster than double
0120 //! linked lists.
0121 //!
0122 //! Important performance note: like every other Sequence, slist defines the member
0123 //! functions insert and erase. Using these member functions carelessly, however, can
0124 //! result in disastrously slow programs. The problem is that insert's first argument is
0125 //! an iterator p, and that it inserts the new element(s) before p. This means that
0126 //! insert must find the iterator just before p; this is a constant-time operation
0127 //! for list, since list has bidirectional iterators, but for slist it must find that
0128 //! iterator by traversing the list from the beginning up to p. In other words:
0129 //! insert and erase are slow operations anywhere but near the beginning of the slist.
0130 //!
0131 //! Slist provides the member functions insert_after and erase_after, which are constant
0132 //! time operations: you should always use insert_after and erase_after whenever
0133 //! possible. If you find that insert_after and erase_after aren't adequate for your
0134 //! needs, and that you often need to use insert and erase in the middle of the list,
0135 //! then you should probably use list instead of slist.
0136 //!
0137 //! \tparam T The type of object that is stored in the list
0138 //! \tparam Allocator The allocator used for all internal memory management, use void
0139 //!   for the default allocator
0140 #ifdef BOOST_CONTAINER_DOXYGEN_INVOKED
0141 template <class T, class Allocator = void >
0142 #else
0143 template <class T, class Allocator>
0144 #endif
0145 class slist
0146    : protected dtl::node_alloc_holder
0147       < typename real_allocator<T, Allocator>::type
0148       , typename dtl::intrusive_slist_type<typename real_allocator<T, Allocator>::type>::type>
0149 {
0150    #ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
0151    typedef typename real_allocator<T, Allocator>::type      ValueAllocator;
0152    typedef typename
0153       dtl::intrusive_slist_type<ValueAllocator>::type       Icont;
0154    typedef dtl::node_alloc_holder<ValueAllocator, Icont>    AllocHolder;
0155    typedef typename AllocHolder::NodePtr                    NodePtr;
0156    typedef typename AllocHolder::NodeAlloc                  NodeAlloc;
0157    typedef typename AllocHolder::ValAlloc                   ValAlloc;
0158    typedef typename AllocHolder::Node                       Node;
0159    typedef dtl::allocator_node_destroyer<NodeAlloc> Destroyer;
0160    typedef typename AllocHolder::alloc_version              alloc_version;
0161    typedef boost::container::
0162       allocator_traits<ValueAllocator>                           allocator_traits_type;
0163    typedef boost::container::equal_to_value
0164       <typename allocator_traits_type::value_type>          equal_to_value_type;
0165 
0166    BOOST_COPYABLE_AND_MOVABLE(slist)
0167    typedef dtl::iterator_from_iiterator<typename Icont::iterator, false>  iterator_impl;
0168    typedef dtl::iterator_from_iiterator<typename Icont::iterator, true >  const_iterator_impl;
0169    #endif   //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
0170 
0171    public:
0172    //////////////////////////////////////////////
0173    //
0174    //                    types
0175    //
0176    //////////////////////////////////////////////
0177 
0178    typedef T                                                                  value_type;
0179    typedef typename ::boost::container::allocator_traits<ValueAllocator>::pointer          pointer;
0180    typedef typename ::boost::container::allocator_traits<ValueAllocator>::const_pointer    const_pointer;
0181    typedef typename ::boost::container::allocator_traits<ValueAllocator>::reference        reference;
0182    typedef typename ::boost::container::allocator_traits<ValueAllocator>::const_reference  const_reference;
0183    typedef typename ::boost::container::allocator_traits<ValueAllocator>::size_type        size_type;
0184    typedef typename ::boost::container::allocator_traits<ValueAllocator>::difference_type  difference_type;
0185    typedef ValueAllocator                                                                  allocator_type;
0186    typedef BOOST_CONTAINER_IMPDEF(NodeAlloc)                                  stored_allocator_type;
0187    typedef BOOST_CONTAINER_IMPDEF(iterator_impl)                              iterator;
0188    typedef BOOST_CONTAINER_IMPDEF(const_iterator_impl)                        const_iterator;
0189 
0190    public:
0191 
0192    //////////////////////////////////////////////
0193    //
0194    //          constructFr/copy/destroy
0195    //
0196    //////////////////////////////////////////////
0197 
0198    //! <b>Effects</b>: Constructs a list taking the allocator as parameter.
0199    //!
0200    //! <b>Throws</b>: If allocator_type's copy constructor throws.
0201    //!
0202    //! <b>Complexity</b>: Constant.
0203    slist() BOOST_NOEXCEPT_IF(dtl::is_nothrow_default_constructible<ValueAllocator>::value)
0204       :  AllocHolder()
0205    {}
0206 
0207    //! <b>Effects</b>: Constructs a list taking the allocator as parameter.
0208    //!
0209    //! <b>Throws</b>: Nothing
0210    //!
0211    //! <b>Complexity</b>: Constant.
0212    explicit slist(const allocator_type& a) BOOST_NOEXCEPT_OR_NOTHROW
0213       :  AllocHolder(a)
0214    {}
0215 
0216    //! <b>Effects</b>: Constructs a list
0217    //!   and inserts n value-initialized value_types.
0218    //!
0219    //! <b>Throws</b>: If allocator_type's default constructor
0220    //!   throws or T's default or copy constructor throws.
0221    //!
0222    //! <b>Complexity</b>: Linear to n.
0223    explicit slist(size_type n)
0224       :  AllocHolder(allocator_type())
0225    { this->resize(n); }
0226 
0227    //! <b>Effects</b>: Constructs a list that will use a copy of allocator a
0228    //!   and inserts n copies of value.
0229    //!
0230    //! <b>Throws</b>: If allocator_type's default constructor
0231    //!   throws or T's default or copy constructor throws.
0232    //!
0233    //! <b>Complexity</b>: Linear to n.
0234    slist(size_type n, const allocator_type &a)
0235       : AllocHolder(a)
0236    {  this->resize(n);  }
0237 
0238    //! <b>Effects</b>: Constructs a list that will use a copy of allocator a
0239    //!   and inserts n copies of value.
0240    //!
0241    //! <b>Throws</b>: If allocator_type's default constructor
0242    //!   throws or T's default or copy constructor throws.
0243    //!
0244    //! <b>Complexity</b>: Linear to n.
0245    explicit slist(size_type n, const value_type& x, const allocator_type& a = allocator_type())
0246       :  AllocHolder(a)
0247    { this->insert_after(this->cbefore_begin(), n, x); }
0248 
0249    //! <b>Effects</b>: Constructs a list that will use a copy of allocator a
0250    //!   and inserts a copy of the range [first, last) in the list.
0251    //!
0252    //! <b>Throws</b>: If allocator_type's default constructor
0253    //!   throws or T's constructor taking a dereferenced InIt throws.
0254    //!
0255    //! <b>Complexity</b>: Linear to the range [first, last).
0256    template <class InpIt>
0257    slist(InpIt first, InpIt last, const allocator_type& a =  allocator_type())
0258       : AllocHolder(a)
0259    { this->insert_after(this->cbefore_begin(), first, last); }
0260 
0261 #if !defined(BOOST_NO_CXX11_HDR_INITIALIZER_LIST)
0262    //! <b>Effects</b>: Constructs a list that will use a copy of allocator a
0263    //!   and inserts a copy of the range [il.begin(), il.end()) in the list.
0264    //!
0265    //! <b>Throws</b>: If allocator_type's default constructor
0266    //!   throws or T's constructor taking a dereferenced std::initializer_list iterator throws.
0267    //!
0268    //! <b>Complexity</b>: Linear to the range [il.begin(), il.end()).
0269    slist(std::initializer_list<value_type> il, const allocator_type& a = allocator_type())
0270       : AllocHolder(a)
0271    { this->insert_after(this->cbefore_begin(), il.begin(), il.end()); }
0272 #endif
0273 
0274     //! <b>Effects</b>: Copy constructs a list.
0275    //!
0276    //! <b>Postcondition</b>: x == *this.
0277    //!
0278    //! <b>Throws</b>: If allocator_type's default constructor
0279    //!
0280    //! <b>Complexity</b>: Linear to the elements x contains.
0281    slist(const slist& x)
0282       : AllocHolder(x)
0283    { this->insert_after(this->cbefore_begin(), x.begin(), x.end()); }
0284 
0285    //! <b>Effects</b>: Move constructor. Moves x's resources to *this.
0286    //!
0287    //! <b>Throws</b>: If allocator_type's copy constructor throws.
0288    //!
0289    //! <b>Complexity</b>: Constant.
0290    slist(BOOST_RV_REF(slist) x) BOOST_NOEXCEPT_OR_NOTHROW
0291       : AllocHolder(BOOST_MOVE_BASE(AllocHolder, x))
0292    {}
0293 
0294    //! <b>Effects</b>: Copy constructs a list using the specified allocator.
0295    //!
0296    //! <b>Postcondition</b>: x == *this.
0297    //!
0298    //! <b>Throws</b>: If allocator_type's default constructor
0299    //!
0300    //! <b>Complexity</b>: Linear to the elements x contains.
0301    slist(const slist& x, const allocator_type &a)
0302       : AllocHolder(a)
0303    { this->insert_after(this->cbefore_begin(), x.begin(), x.end()); }
0304 
0305    //! <b>Effects</b>: Move constructor using the specified allocator.
0306    //!                 Moves x's resources to *this.
0307    //!
0308    //! <b>Throws</b>: If allocation or value_type's copy constructor throws.
0309    //!
0310    //! <b>Complexity</b>: Constant if a == x.get_allocator(), linear otherwise.
0311    slist(BOOST_RV_REF(slist) x, const allocator_type &a)
0312       : AllocHolder(a)
0313    {
0314       slist & sr = x;
0315       if(this->node_alloc() == sr.node_alloc()){
0316          this->icont().swap(sr.icont());
0317       }
0318       else{
0319          this->insert_after(this->cbefore_begin(), boost::make_move_iterator(sr.begin()), boost::make_move_iterator(sr.end()));
0320       }
0321    }
0322 
0323    //! <b>Effects</b>: Destroys the list. All stored values are destroyed
0324    //!   and used memory is deallocated.
0325    //!
0326    //! <b>Throws</b>: Nothing.
0327    //!
0328    //! <b>Complexity</b>: Linear to the number of elements.
0329    ~slist() BOOST_NOEXCEPT_OR_NOTHROW
0330    {} //AllocHolder clears the slist
0331 
0332    //! <b>Effects</b>: Makes *this contain the same elements as x.
0333    //!
0334    //! <b>Postcondition</b>: this->size() == x.size(). *this contains a copy
0335    //! of each of x's elements.
0336    //!
0337    //! <b>Throws</b>: If memory allocation throws or T's copy constructor throws.
0338    //!
0339    //! <b>Complexity</b>: Linear to the number of elements in x.
0340    slist& operator= (BOOST_COPY_ASSIGN_REF(slist) x)
0341    {
0342       if (BOOST_LIKELY(this != &x)) {
0343          NodeAlloc &this_alloc     = this->node_alloc();
0344          const NodeAlloc &x_alloc  = x.node_alloc();
0345          dtl::bool_<allocator_traits_type::
0346             propagate_on_container_copy_assignment::value> flag;
0347          if(flag && this_alloc != x_alloc){
0348             this->clear();
0349          }
0350          this->AllocHolder::copy_assign_alloc(x);
0351          this->assign(x.begin(), x.end());
0352       }
0353       return *this;
0354    }
0355 
0356    //! <b>Effects</b>: Makes *this contain the same elements as x.
0357    //!
0358    //! <b>Postcondition</b>: this->size() == x.size(). *this contains a copy
0359    //! of each of x's elements.
0360    //!
0361    //! <b>Throws</b>: If allocator_traits_type::propagate_on_container_move_assignment
0362    //!   is false and (allocation throws or value_type's move constructor throws)
0363    //!
0364    //! <b>Complexity</b>: Constant if allocator_traits_type::
0365    //!   propagate_on_container_move_assignment is true or
0366    //!   this->get>allocator() == x.get_allocator(). Linear otherwise.
0367    slist& operator=(BOOST_RV_REF(slist) x)
0368       BOOST_NOEXCEPT_IF(allocator_traits_type::propagate_on_container_move_assignment::value
0369                                   || allocator_traits_type::is_always_equal::value)
0370    {
0371       if (BOOST_LIKELY(this != &x)) {
0372          //We know resources can be transferred at comiple time if both allocators are
0373          //always equal or the allocator is going to be propagated
0374          const bool can_steal_resources_alloc
0375             =  allocator_traits_type::propagate_on_container_move_assignment::value
0376             || allocator_traits_type::is_always_equal::value;
0377          dtl::bool_<can_steal_resources_alloc> flag;
0378          this->priv_move_assign(boost::move(x), flag);
0379       }
0380       return *this;
0381    }
0382 
0383 #if !defined(BOOST_NO_CXX11_HDR_INITIALIZER_LIST)
0384    //! <b>Effects</b>: Makes *this contain the same elements as in il.
0385    //!
0386    //! <b>Postcondition</b>: this->size() == il.size(). *this contains a copy
0387    //! of each of il's elements.
0388    //!
0389    //! <b>Throws</b>: If allocator_traits_type::propagate_on_container_move_assignment
0390    //!   is false and (allocation throws or value_type's move constructor throws)
0391    slist& operator=(std::initializer_list<value_type> il)
0392    {
0393        assign(il.begin(), il.end());
0394        return *this;
0395    }
0396 #endif
0397 
0398    //! <b>Effects</b>: Assigns the n copies of val to *this.
0399    //!
0400    //! <b>Throws</b>: If memory allocation throws or T's copy constructor throws.
0401    //!
0402    //! <b>Complexity</b>: Linear to n.
0403    void assign(size_type n, const T& val)
0404    {
0405       typedef constant_iterator<value_type> cvalue_iterator;
0406       return this->assign(cvalue_iterator(val, n), cvalue_iterator());
0407    }
0408 
0409    //! <b>Effects</b>: Assigns the range [first, last) to *this.
0410    //!
0411    //! <b>Throws</b>: If memory allocation throws or
0412    //!   T's constructor from dereferencing InpIt throws.
0413    //!
0414    //! <b>Complexity</b>: Linear to n.
0415    template <class InpIt>
0416    void assign(InpIt first, InpIt last
0417       #if !defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
0418       , typename dtl::disable_if_convertible<InpIt, size_type>::type * = 0
0419       #endif
0420       )
0421    {
0422       iterator end_n(this->end());
0423       iterator prev(this->before_begin());
0424       iterator node(this->begin());
0425       while (node != end_n && first != last){
0426          *node = *first;
0427          prev = node;
0428          ++node;
0429          ++first;
0430       }
0431       if (first != last)
0432          this->insert_after(prev, first, last);
0433       else
0434          this->erase_after(prev, end_n);
0435    }
0436 
0437 #if !defined(BOOST_NO_CXX11_HDR_INITIALIZER_LIST)
0438    //! <b>Effects</b>: Assigns the range [il.begin(), il.end()) to *this.
0439    //!
0440    //! <b>Throws</b>: If memory allocation throws or
0441    //!   T's constructor from dereferencing std::initializer_list iterator throws.
0442    //!
0443    //! <b>Complexity</b>: Linear to range [il.begin(), il.end()).
0444 
0445    void assign(std::initializer_list<value_type> il)
0446    {
0447        assign(il.begin(), il.end());
0448    }
0449 #endif
0450    //! <b>Effects</b>: Returns a copy of the internal allocator.
0451    //!
0452    //! <b>Throws</b>: If allocator's copy constructor throws.
0453    //!
0454    //! <b>Complexity</b>: Constant.
0455    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0456       allocator_type get_allocator() const BOOST_NOEXCEPT_OR_NOTHROW
0457    {  return allocator_type(this->node_alloc()); }
0458 
0459    //! <b>Effects</b>: Returns a reference to the internal allocator.
0460    //!
0461    //! <b>Throws</b>: Nothing
0462    //!
0463    //! <b>Complexity</b>: Constant.
0464    //!
0465    //! <b>Note</b>: Non-standard extension.
0466    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0467       stored_allocator_type &get_stored_allocator() BOOST_NOEXCEPT_OR_NOTHROW
0468    {  return this->node_alloc(); }
0469 
0470    //! <b>Effects</b>: Returns a reference to the internal allocator.
0471    //!
0472    //! <b>Throws</b>: Nothing
0473    //!
0474    //! <b>Complexity</b>: Constant.
0475    //!
0476    //! <b>Note</b>: Non-standard extension.
0477    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0478       const stored_allocator_type &get_stored_allocator() const BOOST_NOEXCEPT_OR_NOTHROW
0479    {  return this->node_alloc(); }
0480 
0481    //////////////////////////////////////////////
0482    //
0483    //                iterators
0484    //
0485    //////////////////////////////////////////////
0486 
0487    //! <b>Effects</b>: Returns a non-dereferenceable iterator that,
0488    //! when incremented, yields begin().  This iterator may be used
0489    //! as the argument to insert_after, erase_after, etc.
0490    //!
0491    //! <b>Throws</b>: Nothing.
0492    //!
0493    //! <b>Complexity</b>: Constant.
0494    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0495       iterator before_begin() BOOST_NOEXCEPT_OR_NOTHROW
0496    {  return iterator(end());  }
0497 
0498    //! <b>Effects</b>: Returns a non-dereferenceable const_iterator
0499    //! that, when incremented, yields begin().  This iterator may be used
0500    //! as the argument to insert_after, erase_after, etc.
0501    //!
0502    //! <b>Throws</b>: Nothing.
0503    //!
0504    //! <b>Complexity</b>: Constant.
0505    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0506       const_iterator before_begin() const BOOST_NOEXCEPT_OR_NOTHROW
0507    {  return this->cbefore_begin();  }
0508 
0509    //! <b>Effects</b>: Returns an iterator to the first element contained in the list.
0510    //!
0511    //! <b>Throws</b>: Nothing.
0512    //!
0513    //! <b>Complexity</b>: Constant.
0514    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0515       iterator begin() BOOST_NOEXCEPT_OR_NOTHROW
0516    { return iterator(this->icont().begin()); }
0517 
0518    //! <b>Effects</b>: Returns a const_iterator to the first element contained in the list.
0519    //!
0520    //! <b>Throws</b>: Nothing.
0521    //!
0522    //! <b>Complexity</b>: Constant.
0523    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0524       const_iterator begin() const BOOST_NOEXCEPT_OR_NOTHROW
0525    {  return this->cbegin();   }
0526 
0527    //! <b>Effects</b>: Returns an iterator to the end of the list.
0528    //!
0529    //! <b>Throws</b>: Nothing.
0530    //!
0531    //! <b>Complexity</b>: Constant.
0532    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0533       iterator end() BOOST_NOEXCEPT_OR_NOTHROW
0534    { return iterator(this->icont().end()); }
0535 
0536    //! <b>Effects</b>: Returns a const_iterator to the end of the list.
0537    //!
0538    //! <b>Throws</b>: Nothing.
0539    //!
0540    //! <b>Complexity</b>: Constant.
0541    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0542       const_iterator end() const BOOST_NOEXCEPT_OR_NOTHROW
0543    {  return this->cend();   }
0544 
0545    //! <b>Effects</b>: Returns a non-dereferenceable const_iterator
0546    //! that, when incremented, yields begin().  This iterator may be used
0547    //! as the argument to insert_after, erase_after, etc.
0548    //!
0549    //! <b>Throws</b>: Nothing.
0550    //!
0551    //! <b>Complexity</b>: Constant.
0552    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0553       const_iterator cbefore_begin() const BOOST_NOEXCEPT_OR_NOTHROW
0554    {  return const_iterator(end());  }
0555 
0556    //! <b>Effects</b>: Returns a const_iterator to the first element contained in the list.
0557    //!
0558    //! <b>Throws</b>: Nothing.
0559    //!
0560    //! <b>Complexity</b>: Constant.
0561    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0562       const_iterator cbegin() const BOOST_NOEXCEPT_OR_NOTHROW
0563    {  return const_iterator(this->non_const_icont().begin());   }
0564 
0565    //! <b>Effects</b>: Returns a const_iterator to the end of the list.
0566    //!
0567    //! <b>Throws</b>: Nothing.
0568    //!
0569    //! <b>Complexity</b>: Constant.
0570    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0571       const_iterator cend() const BOOST_NOEXCEPT_OR_NOTHROW
0572    {  return const_iterator(this->non_const_icont().end());   }
0573 
0574    //! <b>Returns</b>: The iterator to the element before i in the sequence.
0575    //!   Returns the end-iterator, if either i is the begin-iterator or the
0576    //!   sequence is empty.
0577    //!
0578    //! <b>Throws</b>: Nothing.
0579    //!
0580    //! <b>Complexity</b>: Linear to the number of elements before i.
0581    //!
0582    //! <b>Note</b>: Non-standard extension.
0583    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0584       iterator previous(iterator p) BOOST_NOEXCEPT_OR_NOTHROW
0585    {  return iterator(this->icont().previous(p.get())); }
0586 
0587    //! <b>Returns</b>: The const_iterator to the element before i in the sequence.
0588    //!   Returns the end-const_iterator, if either i is the begin-const_iterator or
0589    //!   the sequence is empty.
0590    //!
0591    //! <b>Throws</b>: Nothing.
0592    //!
0593    //! <b>Complexity</b>: Linear to the number of elements before i.
0594    //!
0595    //! <b>Note</b>: Non-standard extension.
0596    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0597       const_iterator previous(const_iterator p)
0598    {  return const_iterator(this->icont().previous(p.get())); }
0599 
0600    //////////////////////////////////////////////
0601    //
0602    //                capacity
0603    //
0604    //////////////////////////////////////////////
0605 
0606    //! <b>Effects</b>: Returns true if the list contains no elements.
0607    //!
0608    //! <b>Throws</b>: Nothing.
0609    //!
0610    //! <b>Complexity</b>: Constant.
0611    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0612       bool empty() const
0613    {  return !this->size();   }
0614 
0615    //! <b>Effects</b>: Returns the number of the elements contained in the list.
0616    //!
0617    //! <b>Throws</b>: Nothing.
0618    //!
0619    //! <b>Complexity</b>: Constant.
0620    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0621       size_type size() const
0622    {  return this->icont().size(); }
0623 
0624    //! <b>Effects</b>: Returns the largest possible size of the list.
0625    //!
0626    //! <b>Throws</b>: Nothing.
0627    //!
0628    //! <b>Complexity</b>: Constant.
0629    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0630       size_type max_size() const
0631    {  return AllocHolder::max_size();  }
0632 
0633    //! <b>Effects</b>: Inserts or erases elements at the end such that
0634    //!   the size becomes n. New elements are value initialized.
0635    //!
0636    //! <b>Throws</b>: If memory allocation throws, or T's copy constructor throws.
0637    //!
0638    //! <b>Complexity</b>: Linear to the difference between size() and new_size.
0639    void resize(size_type new_size)
0640    {
0641       const_iterator last_pos;
0642       if(!priv_try_shrink(new_size, last_pos)){
0643          typedef value_init_construct_iterator<value_type> value_init_iterator;
0644          this->insert_after(last_pos, value_init_iterator(new_size - this->size()), value_init_iterator());
0645       }
0646    }
0647 
0648    //! <b>Effects</b>: Inserts or erases elements at the end such that
0649    //!   the size becomes n. New elements are copy constructed from x.
0650    //!
0651    //! <b>Throws</b>: If memory allocation throws, or T's copy constructor throws.
0652    //!
0653    //! <b>Complexity</b>: Linear to the difference between size() and new_size.
0654    void resize(size_type new_size, const T& x)
0655    {
0656       const_iterator last_pos;
0657       if(!priv_try_shrink(new_size, last_pos)){
0658          this->insert_after(last_pos, new_size, x);
0659       }
0660    }
0661 
0662    //////////////////////////////////////////////
0663    //
0664    //               element access
0665    //
0666    //////////////////////////////////////////////
0667 
0668    //! <b>Requires</b>: !empty()
0669    //!
0670    //! <b>Effects</b>: Returns a reference to the first element
0671    //!   from the beginning of the container.
0672    //!
0673    //! <b>Throws</b>: Nothing.
0674    //!
0675    //! <b>Complexity</b>: Constant.
0676    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0677       reference front()
0678    {
0679       BOOST_ASSERT(!this->empty());
0680       return *this->begin();
0681    }
0682 
0683    //! <b>Requires</b>: !empty()
0684    //!
0685    //! <b>Effects</b>: Returns a const reference to the first element
0686    //!   from the beginning of the container.
0687    //!
0688    //! <b>Throws</b>: Nothing.
0689    //!
0690    //! <b>Complexity</b>: Constant.
0691    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
0692       const_reference front() const
0693    {
0694       BOOST_ASSERT(!this->empty());
0695       return *this->begin();
0696    }
0697 
0698    //////////////////////////////////////////////
0699    //
0700    //                modifiers
0701    //
0702    //////////////////////////////////////////////
0703 
0704    #if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
0705 
0706    //! <b>Effects</b>: Inserts an object of type T constructed with
0707    //!   std::forward<Args>(args)... in the front of the list
0708    //!
0709    //! <b>Returns</b>: A reference to the created object.
0710    //!
0711    //! <b>Throws</b>: If memory allocation throws or
0712    //!   T's copy constructor throws.
0713    //!
0714    //! <b>Complexity</b>: Amortized constant time.
0715    template <class... Args>
0716    reference emplace_front(BOOST_FWD_REF(Args)... args)
0717    {  return *this->emplace_after(this->cbefore_begin(), boost::forward<Args>(args)...); }
0718 
0719    //! <b>Effects</b>: Inserts an object of type T constructed with
0720    //!   std::forward<Args>(args)... after prev
0721    //!
0722    //! <b>Throws</b>: If memory allocation throws or
0723    //!   T's in-place constructor throws.
0724    //!
0725    //! <b>Complexity</b>: Constant
0726    template <class... Args>
0727    iterator emplace_after(const_iterator prev, BOOST_FWD_REF(Args)... args)
0728    {
0729       NodePtr pnode(AllocHolder::create_node(boost::forward<Args>(args)...));
0730       return iterator(this->icont().insert_after(prev.get(), *pnode));
0731    }
0732 
0733    #else // !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
0734 
0735    #define BOOST_CONTAINER_SLIST_EMPLACE_CODE(N) \
0736    BOOST_MOVE_TMPL_LT##N BOOST_MOVE_CLASS##N BOOST_MOVE_GT##N \
0737    reference emplace_front(BOOST_MOVE_UREF##N)\
0738    {  return *this->emplace_after(this->cbefore_begin() BOOST_MOVE_I##N BOOST_MOVE_FWD##N);}\
0739    \
0740    BOOST_MOVE_TMPL_LT##N BOOST_MOVE_CLASS##N BOOST_MOVE_GT##N \
0741    iterator emplace_after(const_iterator p BOOST_MOVE_I##N BOOST_MOVE_UREF##N)\
0742    {\
0743       NodePtr pnode (AllocHolder::create_node(BOOST_MOVE_FWD##N));\
0744       return iterator(this->icont().insert_after(p.get(), *pnode));\
0745    }\
0746    //
0747    BOOST_MOVE_ITERATE_0TO9(BOOST_CONTAINER_SLIST_EMPLACE_CODE)
0748    #undef BOOST_CONTAINER_SLIST_EMPLACE_CODE
0749 
0750    #endif   // !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
0751 
0752    #if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
0753    //! <b>Effects</b>: Inserts a copy of x at the beginning of the list.
0754    //!
0755    //! <b>Throws</b>: If memory allocation throws or
0756    //!   T's copy constructor throws.
0757    //!
0758    //! <b>Complexity</b>: Amortized constant time.
0759    void push_front(const T &x);
0760 
0761    //! <b>Effects</b>: Constructs a new element in the beginning of the list
0762    //!   and moves the resources of x to this new element.
0763    //!
0764    //! <b>Throws</b>: If memory allocation throws.
0765    //!
0766    //! <b>Complexity</b>: Amortized constant time.
0767    void push_front(T &&x);
0768    #else
0769    BOOST_MOVE_CONVERSION_AWARE_CATCH(push_front, T, void, priv_push_front)
0770    #endif
0771 
0772 
0773    #if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
0774    //! <b>Requires</b>: p must be a valid iterator of *this.
0775    //!
0776    //! <b>Effects</b>: Inserts a copy of the value after prev_p.
0777    //!
0778    //! <b>Returns</b>: An iterator to the inserted element.
0779    //!
0780    //! <b>Throws</b>: If memory allocation throws or T's copy constructor throws.
0781    //!
0782    //! <b>Complexity</b>: Amortized constant time.
0783    //!
0784    //! <b>Note</b>: Does not affect the validity of iterators and references of
0785    //!   previous values.
0786    iterator insert_after(const_iterator prev_p, const T &x);
0787 
0788    //! <b>Requires</b>: prev_p must be a valid iterator of *this.
0789    //!
0790    //! <b>Effects</b>: Inserts a move constructed copy object from the value after the
0791    //!    element pointed by prev_p.
0792    //!
0793    //! <b>Returns</b>: An iterator to the inserted element.
0794    //!
0795    //! <b>Throws</b>: If memory allocation throws.
0796    //!
0797    //! <b>Complexity</b>: Amortized constant time.
0798    //!
0799    //! <b>Note</b>: Does not affect the validity of iterators and references of
0800    //!   previous values.
0801    iterator insert_after(const_iterator prev_p, T &&x);
0802    #else
0803    BOOST_MOVE_CONVERSION_AWARE_CATCH_1ARG(insert_after, T, iterator, priv_insert_after, const_iterator, const_iterator)
0804    #endif
0805 
0806    //! <b>Requires</b>: prev_p must be a valid iterator of *this.
0807    //!
0808    //! <b>Effects</b>: Inserts n copies of x after prev_p.
0809    //!
0810    //! <b>Returns</b>: an iterator to the last inserted element or prev_p if n is 0.
0811    //!
0812    //! <b>Throws</b>: If memory allocation throws or T's copy constructor throws.
0813    //!
0814    //!
0815    //! <b>Complexity</b>: Linear to n.
0816    //!
0817    //! <b>Note</b>: Does not affect the validity of iterators and references of
0818    //!   previous values.
0819    iterator insert_after(const_iterator prev_p, size_type n, const value_type& x)
0820    {
0821       typedef constant_iterator<value_type> cvalue_iterator;
0822       return this->insert_after(prev_p, cvalue_iterator(x, n), cvalue_iterator());
0823    }
0824 
0825    //! <b>Requires</b>: prev_p must be a valid iterator of *this.
0826    //!
0827    //! <b>Effects</b>: Inserts the range pointed by [first, last) after prev_p.
0828    //!
0829    //! <b>Returns</b>: an iterator to the last inserted element or prev_p if first == last.
0830    //!
0831    //! <b>Throws</b>: If memory allocation throws, T's constructor from a
0832    //!   dereferenced InpIt throws.
0833    //!
0834    //! <b>Complexity</b>: Linear to the number of elements inserted.
0835    //!
0836    //! <b>Note</b>: Does not affect the validity of iterators and references of
0837    //!   previous values.
0838    template <class InpIt>
0839    iterator insert_after(const_iterator prev_p, InpIt first, InpIt last
0840       #if !defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
0841       , typename dtl::enable_if_c
0842          < !dtl::is_convertible<InpIt, size_type>::value
0843           && (dtl::is_input_iterator<InpIt>::value
0844                 || dtl::is_same<alloc_version, version_1>::value
0845                )
0846          >::type * = 0
0847       #endif
0848       )
0849    {
0850       iterator ret_it(prev_p.get());
0851       for (; first != last; ++first){
0852          ret_it = iterator(this->icont().insert_after(ret_it.get(), *this->create_node_from_it(first)));
0853       }
0854       return ret_it;
0855    }
0856 
0857 #if !defined(BOOST_NO_CXX11_HDR_INITIALIZER_LIST)
0858    //! <b>Requires</b>: prev_p must be a valid iterator of *this.
0859    //!
0860    //! <b>Effects</b>: Inserts the range pointed by [il.begin(), il.end()) after prev_p.
0861    //!
0862    //! <b>Returns</b>: an iterator to the last inserted element or prev_p if il.begin() == il.end().
0863    //!
0864    //! <b>Throws</b>: If memory allocation throws, T's constructor from a
0865    //!   dereferenced std::initializer_list iterator throws.
0866    //!
0867    //! <b>Complexity</b>: Linear to the number of elements inserted.
0868    //!
0869    //! <b>Note</b>: Does not affect the validity of iterators and references of
0870    //!   previous values.
0871    iterator insert_after(const_iterator prev_p, std::initializer_list<value_type> il)
0872    {
0873        return insert_after(prev_p, il.begin(), il.end());
0874    }
0875 #endif
0876    #if !defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
0877    template <class FwdIt>
0878    iterator insert_after(const_iterator prev, FwdIt first, FwdIt last
0879       , typename dtl::enable_if_c
0880          < !dtl::is_convertible<FwdIt, size_type>::value
0881             && !(dtl::is_input_iterator<FwdIt>::value
0882                 || dtl::is_same<alloc_version, version_1>::value
0883                )
0884          >::type * = 0
0885       )
0886    {
0887       //Optimized allocation and construction
0888       insertion_functor func(this->icont(), prev.get());
0889       this->allocate_many_and_construct(first, boost::container::iterator_udistance(first, last), func);
0890       return iterator(func.inserted_first());
0891    }
0892    #endif
0893 
0894    //! <b>Effects</b>: Removes the first element from the list.
0895    //!
0896    //! <b>Throws</b>: Nothing.
0897    //!
0898    //! <b>Complexity</b>: Amortized constant time.
0899    void pop_front()
0900    {
0901       BOOST_ASSERT(!this->empty());
0902       this->icont().pop_front_and_dispose(Destroyer(this->node_alloc()));
0903    }
0904 
0905    //! <b>Effects</b>: Erases the element after the element pointed by prev_p
0906    //!    of the list.
0907    //!
0908    //! <b>Returns</b>: the first element remaining beyond the removed elements,
0909    //!   or end() if no such element exists.
0910    //!
0911    //! <b>Throws</b>: Nothing.
0912    //!
0913    //! <b>Complexity</b>: Constant.
0914    //!
0915    //! <b>Note</b>: Does not invalidate iterators or references to non erased elements.
0916    iterator erase_after(const_iterator prev_p)
0917    {
0918       return iterator(this->icont().erase_after_and_dispose(prev_p.get(), Destroyer(this->node_alloc())));
0919    }
0920 
0921    //! <b>Effects</b>: Erases the range (before_first, last) from
0922    //!   the list.
0923    //!
0924    //! <b>Returns</b>: the first element remaining beyond the removed elements,
0925    //!   or end() if no such element exists.
0926    //!
0927    //! <b>Throws</b>: Nothing.
0928    //!
0929    //! <b>Complexity</b>: Linear to the number of erased elements.
0930    //!
0931    //! <b>Note</b>: Does not invalidate iterators or references to non erased elements.
0932    iterator erase_after(const_iterator before_first, const_iterator last)
0933    {
0934       return iterator(this->icont().erase_after_and_dispose(before_first.get(), last.get(), Destroyer(this->node_alloc())));
0935    }
0936 
0937    //! <b>Effects</b>: Swaps the contents of *this and x.
0938    //!
0939    //! <b>Throws</b>: Nothing.
0940    //!
0941    //! <b>Complexity</b>: Linear to the number of elements on *this and x.
0942    void swap(slist& x)
0943       BOOST_NOEXCEPT_IF( allocator_traits_type::propagate_on_container_swap::value
0944                                 || allocator_traits_type::is_always_equal::value)
0945    {
0946       BOOST_ASSERT(allocator_traits_type::propagate_on_container_swap::value ||
0947                    allocator_traits_type::is_always_equal::value ||
0948                    this->get_stored_allocator() == x.get_stored_allocator());
0949       AllocHolder::swap(x);
0950    }
0951 
0952    //! <b>Effects</b>: Erases all the elements of the list.
0953    //!
0954    //! <b>Throws</b>: Nothing.
0955    //!
0956    //! <b>Complexity</b>: Linear to the number of elements in the list.
0957    void clear()
0958    {  this->icont().clear_and_dispose(Destroyer(this->node_alloc()));  }
0959 
0960    //////////////////////////////////////////////
0961    //
0962    //              slist operations
0963    //
0964    //////////////////////////////////////////////
0965 
0966    //! <b>Requires</b>: p must point to an element contained
0967    //!   by the list. x != *this
0968    //!
0969    //! <b>Effects</b>: Transfers all the elements of list x to this list, after the
0970    //!   the element pointed by p. No destructors or copy constructors are called.
0971    //!
0972    //! <b>Throws</b>: runtime_error if this' allocator and x's allocator
0973    //!   are not equal.
0974    //!
0975    //! <b>Complexity</b>: Linear to the elements in x.
0976    //!
0977    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of
0978    //!    this list. Iterators of this list and all the references are not invalidated.
0979    void splice_after(const_iterator prev_p, slist& x) BOOST_NOEXCEPT_OR_NOTHROW
0980    {
0981       BOOST_ASSERT(this != &x);
0982       BOOST_ASSERT(this->node_alloc() == x.node_alloc());
0983       this->icont().splice_after(prev_p.get(), x.icont());
0984    }
0985 
0986    //! <b>Requires</b>: p must point to an element contained
0987    //!   by the list. x != *this
0988    //!
0989    //! <b>Effects</b>: Transfers all the elements of list x to this list, after the
0990    //!   the element pointed by p. No destructors or copy constructors are called.
0991    //!
0992    //! <b>Throws</b>: runtime_error if this' allocator and x's allocator
0993    //!   are not equal.
0994    //!
0995    //! <b>Complexity</b>: Linear to the elements in x.
0996    //!
0997    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of
0998    //!    this list. Iterators of this list and all the references are not invalidated.
0999    void splice_after(const_iterator prev_p, BOOST_RV_REF(slist) x) BOOST_NOEXCEPT_OR_NOTHROW
1000    {  this->splice_after(prev_p, BOOST_MOVE_TO_LV(x));  }
1001 
1002    //! <b>Requires</b>: prev_p must be a valid iterator of this.
1003    //!   i must point to an element contained in list x.
1004    //!   this' allocator and x's allocator shall compare equal.
1005    //!
1006    //! <b>Effects</b>: Transfers the value pointed by i, from list x to this list,
1007    //!   after the element pointed by prev_p.
1008    //!   If prev_p == prev or prev_p == ++prev, this function is a null operation.
1009    //!
1010    //! <b>Throws</b>: Nothing
1011    //!
1012    //! <b>Complexity</b>: Constant.
1013    //!
1014    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1015    //!   list. Iterators of this list and all the references are not invalidated.
1016    void splice_after(const_iterator prev_p, slist& x, const_iterator prev) BOOST_NOEXCEPT_OR_NOTHROW
1017    {
1018       BOOST_ASSERT(this->node_alloc() == x.node_alloc());
1019       this->icont().splice_after(prev_p.get(), x.icont(), prev.get());
1020    }
1021 
1022    //! <b>Requires</b>: prev_p must be a valid iterator of this.
1023    //!   i must point to an element contained in list x.
1024    //!   this' allocator and x's allocator shall compare equal.
1025    //!
1026    //! <b>Effects</b>: Transfers the value pointed by i, from list x to this list,
1027    //!   after the element pointed by prev_p.
1028    //!   If prev_p == prev or prev_p == ++prev, this function is a null operation.
1029    //!
1030    //! <b>Throws</b>: Nothing
1031    //!
1032    //! <b>Complexity</b>: Constant.
1033    //!
1034    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1035    //!   list. Iterators of this list and all the references are not invalidated.
1036    void splice_after(const_iterator prev_p, BOOST_RV_REF(slist) x, const_iterator prev) BOOST_NOEXCEPT_OR_NOTHROW
1037    {  this->splice_after(prev_p, BOOST_MOVE_TO_LV(x), prev);  }
1038 
1039    //! <b>Requires</b>: prev_p must be a valid iterator of this.
1040    //!   before_first and before_last must be valid iterators of x.
1041    //!   prev_p must not be contained in [before_first, before_last) range.
1042    //!   this' allocator and x's allocator shall compare equal.
1043    //!
1044    //! <b>Effects</b>: Transfers the range [before_first + 1, before_last + 1)
1045    //!   from list x to this list, after the element pointed by prev_p.
1046    //!
1047    //! <b>Throws</b>: Nothing
1048    //!
1049    //! <b>Complexity</b>: Linear to the number of transferred elements.
1050    //!
1051    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1052    //!   list. Iterators of this list and all the references are not invalidated.
1053    void splice_after(const_iterator prev_p,      slist& x,
1054       const_iterator before_first,  const_iterator before_last) BOOST_NOEXCEPT_OR_NOTHROW
1055    {
1056       BOOST_ASSERT(this->node_alloc() == x.node_alloc());
1057       this->icont().splice_after
1058          (prev_p.get(), x.icont(), before_first.get(), before_last.get());
1059    }
1060 
1061    //! <b>Requires</b>: prev_p must be a valid iterator of this.
1062    //!   before_first and before_last must be valid iterators of x.
1063    //!   prev_p must not be contained in [before_first, before_last) range.
1064    //!   this' allocator and x's allocator shall compare equal.
1065    //!
1066    //! <b>Effects</b>: Transfers the range [before_first + 1, before_last + 1)
1067    //!   from list x to this list, after the element pointed by prev_p.
1068    //!
1069    //! <b>Throws</b>: Nothing
1070    //!
1071    //! <b>Complexity</b>: Linear to the number of transferred elements.
1072    //!
1073    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1074    //!   list. Iterators of this list and all the references are not invalidated.
1075    void splice_after(const_iterator prev_p,      BOOST_RV_REF(slist) x,
1076       const_iterator before_first,  const_iterator before_last) BOOST_NOEXCEPT_OR_NOTHROW
1077    {  this->splice_after(prev_p, BOOST_MOVE_TO_LV(x), before_first, before_last);  }
1078 
1079    //! <b>Requires</b>: prev_p must be a valid iterator of this.
1080    //!   before_first and before_last must be valid iterators of x.
1081    //!   prev_p must not be contained in [before_first, before_last) range.
1082    //!   n == distance(before_first, before_last).
1083    //!   this' allocator and x's allocator shall compare equal.
1084    //!
1085    //! <b>Effects</b>: Transfers the range [before_first + 1, before_last + 1)
1086    //!   from list x to this list, after the element pointed by prev_p.
1087    //!
1088    //! <b>Throws</b>: Nothing
1089    //!
1090    //! <b>Complexity</b>: Constant.
1091    //!
1092    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1093    //!   list. Iterators of this list and all the references are not invalidated.
1094    void splice_after(const_iterator prev_p,      slist& x,
1095                      const_iterator before_first,  const_iterator before_last,
1096                      size_type n) BOOST_NOEXCEPT_OR_NOTHROW
1097    {
1098       BOOST_ASSERT(this->node_alloc() == x.node_alloc());
1099       this->icont().splice_after
1100          (prev_p.get(), x.icont(), before_first.get(), before_last.get(), n);
1101    }
1102 
1103    //! <b>Requires</b>: prev_p must be a valid iterator of this.
1104    //!   before_first and before_last must be valid iterators of x.
1105    //!   prev_p must not be contained in [before_first, before_last) range.
1106    //!   n == distance(before_first, before_last).
1107    //!   this' allocator and x's allocator shall compare equal.
1108    //!
1109    //! <b>Effects</b>: Transfers the range [before_first + 1, before_last + 1)
1110    //!   from list x to this list, after the element pointed by prev_p.
1111    //!
1112    //! <b>Throws</b>: Nothing
1113    //!
1114    //! <b>Complexity</b>: Constant.
1115    //!
1116    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1117    //!   list. Iterators of this list and all the references are not invalidated.
1118    void splice_after(const_iterator prev_p,      BOOST_RV_REF(slist) x,
1119                      const_iterator before_first,  const_iterator before_last,
1120                      size_type n) BOOST_NOEXCEPT_OR_NOTHROW
1121    {  this->splice_after(prev_p, BOOST_MOVE_TO_LV(x), before_first, before_last, n);  }
1122 
1123    //! <b>Effects</b>: Removes all the elements that compare equal to value.
1124    //!
1125    //! <b>Throws</b>: Nothing.
1126    //!
1127    //! <b>Complexity</b>: Linear time. It performs exactly size() comparisons for equality.
1128    //!
1129    //! <b>Note</b>: The relative order of elements that are not removed is unchanged,
1130    //!   and iterators to elements that are not removed remain valid.
1131    void remove(const T& value)
1132    {  this->remove_if(equal_to_value_type(value));  }
1133 
1134    //! <b>Effects</b>: Removes all the elements for which a specified
1135    //!   predicate is satisfied.
1136    //!
1137    //! <b>Throws</b>: If pred throws.
1138    //!
1139    //! <b>Complexity</b>: Linear time. It performs exactly size() calls to the predicate.
1140    //!
1141    //! <b>Note</b>: The relative order of elements that are not removed is unchanged,
1142    //!   and iterators to elements that are not removed remain valid.
1143    template <class Pred>
1144    void remove_if(Pred pred)
1145    {
1146       typedef value_to_node_compare<Node, Pred> value_to_node_compare_type;
1147       this->icont().remove_and_dispose_if(value_to_node_compare_type(pred), Destroyer(this->node_alloc()));
1148    }
1149 
1150    //! <b>Effects</b>: Removes adjacent duplicate elements or adjacent
1151    //!   elements that are equal from the list.
1152    //!
1153    //! <b>Throws</b>: If comparison throws.
1154    //!
1155    //! <b>Complexity</b>: Linear time (size()-1 comparisons equality comparisons).
1156    //!
1157    //! <b>Note</b>: The relative order of elements that are not removed is unchanged,
1158    //!   and iterators to elements that are not removed remain valid.
1159    void unique()
1160    {  this->unique(value_equal_t());  }
1161 
1162    //! <b>Effects</b>: Removes adjacent duplicate elements or adjacent
1163    //!   elements that satisfy some binary predicate from the list.
1164    //!
1165    //! <b>Throws</b>: If pred throws.
1166    //!
1167    //! <b>Complexity</b>: Linear time (size()-1 comparisons calls to pred()).
1168    //!
1169    //! <b>Note</b>: The relative order of elements that are not removed is unchanged,
1170    //!   and iterators to elements that are not removed remain valid.
1171    template <class Pred>
1172    void unique(Pred pred)
1173    {
1174       typedef value_to_node_compare<Node, Pred> value_to_node_compare_type;
1175       this->icont().unique_and_dispose(value_to_node_compare_type(pred), Destroyer(this->node_alloc()));
1176    }
1177 
1178    //! <b>Requires</b>: The lists x and *this must be distinct.
1179    //!
1180    //! <b>Effects</b>: This function removes all of x's elements and inserts them
1181    //!   in order into *this according to std::less<value_type>. The merge is stable;
1182    //!   that is, if an element from *this is equivalent to one from x, then the element
1183    //!   from *this will precede the one from x.
1184    //!
1185    //! <b>Throws</b>: If comparison throws.
1186    //!
1187    //! <b>Complexity</b>: This function is linear time: it performs at most
1188    //!   size() + x.size() - 1 comparisons.
1189    void merge(slist & x)
1190    {  this->merge(x, value_less_t()); }
1191 
1192    //! <b>Requires</b>: The lists x and *this must be distinct.
1193    //!
1194    //! <b>Effects</b>: This function removes all of x's elements and inserts them
1195    //!   in order into *this according to std::less<value_type>. The merge is stable;
1196    //!   that is, if an element from *this is equivalent to one from x, then the element
1197    //!   from *this will precede the one from x.
1198    //!
1199    //! <b>Throws</b>: If comparison throws.
1200    //!
1201    //! <b>Complexity</b>: This function is linear time: it performs at most
1202    //!   size() + x.size() - 1 comparisons.
1203    void merge(BOOST_RV_REF(slist) x)
1204    {  this->merge(BOOST_MOVE_TO_LV(x)); }
1205 
1206    //! <b>Requires</b>: p must be a comparison function that induces a strict weak
1207    //!   ordering and both *this and x must be sorted according to that ordering
1208    //!   The lists x and *this must be distinct.
1209    //!
1210    //! <b>Effects</b>: This function removes all of x's elements and inserts them
1211    //!   in order into *this. The merge is stable; that is, if an element from *this is
1212    //!   equivalent to one from x, then the element from *this will precede the one from x.
1213    //!
1214    //! <b>Throws</b>: If comp throws.
1215    //!
1216    //! <b>Complexity</b>: This function is linear time: it performs at most
1217    //!   size() + x.size() - 1 comparisons.
1218    //!
1219    //! <b>Note</b>: Iterators and references to *this are not invalidated.
1220    template <class StrictWeakOrdering>
1221    void merge(slist& x, StrictWeakOrdering comp)
1222    {
1223       typedef value_to_node_compare<Node, StrictWeakOrdering> value_to_node_compare_type;
1224       BOOST_ASSERT(this->node_alloc() == x.node_alloc());
1225       this->icont().merge(x.icont(), value_to_node_compare_type(comp));
1226    }
1227 
1228    //! <b>Requires</b>: p must be a comparison function that induces a strict weak
1229    //!   ordering and both *this and x must be sorted according to that ordering
1230    //!   The lists x and *this must be distinct.
1231    //!
1232    //! <b>Effects</b>: This function removes all of x's elements and inserts them
1233    //!   in order into *this. The merge is stable; that is, if an element from *this is
1234    //!   equivalent to one from x, then the element from *this will precede the one from x.
1235    //!
1236    //! <b>Throws</b>: If comp throws.
1237    //!
1238    //! <b>Complexity</b>: This function is linear time: it performs at most
1239    //!   size() + x.size() - 1 comparisons.
1240    //!
1241    //! <b>Note</b>: Iterators and references to *this are not invalidated.
1242    template <class StrictWeakOrdering>
1243    void merge(BOOST_RV_REF(slist) x, StrictWeakOrdering comp)
1244    {  this->merge(BOOST_MOVE_TO_LV(x), comp); }
1245 
1246    //! <b>Effects</b>: This function sorts the list *this according to std::less<value_type>.
1247    //!   The sort is stable, that is, the relative order of equivalent elements is preserved.
1248    //!
1249    //! <b>Throws</b>: If comparison throws.
1250    //!
1251    //! <b>Notes</b>: Iterators and references are not invalidated.
1252    //!
1253    //! <b>Complexity</b>: The number of comparisons is approximately N log N, where N
1254    //!   is the list's size.
1255    void sort()
1256    {  this->sort(value_less_t());  }
1257 
1258    //! <b>Effects</b>: This function sorts the list *this according to std::less<value_type>.
1259    //!   The sort is stable, that is, the relative order of equivalent elements is preserved.
1260    //!
1261    //! <b>Throws</b>: If comp throws.
1262    //!
1263    //! <b>Notes</b>: Iterators and references are not invalidated.
1264    //!
1265    //! <b>Complexity</b>: The number of comparisons is approximately N log N, where N
1266    //!   is the list's size.
1267    template <class StrictWeakOrdering>
1268    void sort(StrictWeakOrdering comp)
1269    {
1270       typedef value_to_node_compare<Node, StrictWeakOrdering> value_to_node_compare_type;
1271       // nothing if the slist has length 0 or 1.
1272       if (this->size() < 2)
1273          return;
1274       this->icont().sort(value_to_node_compare_type(comp));
1275    }
1276 
1277    //! <b>Effects</b>: Reverses the order of elements in the list.
1278    //!
1279    //! <b>Throws</b>: Nothing.
1280    //!
1281    //! <b>Complexity</b>: This function is linear time.
1282    //!
1283    //! <b>Note</b>: Iterators and references are not invalidated
1284    void reverse() BOOST_NOEXCEPT_OR_NOTHROW
1285    {  this->icont().reverse();  }
1286 
1287    //////////////////////////////////////////////
1288    //
1289    //       list compatibility interface
1290    //
1291    //////////////////////////////////////////////
1292 
1293    #if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
1294 
1295    //! <b>Effects</b>: Inserts an object of type T constructed with
1296    //!   std::forward<Args>(args)... before p
1297    //!
1298    //! <b>Throws</b>: If memory allocation throws or
1299    //!   T's in-place constructor throws.
1300    //!
1301    //! <b>Complexity</b>: Linear to the elements before p
1302    template <class... Args>
1303    iterator emplace(const_iterator p, BOOST_FWD_REF(Args)... args)
1304    {  return this->emplace_after(this->previous(p), boost::forward<Args>(args)...);  }
1305 
1306    #else
1307 
1308    #define BOOST_CONTAINER_SLIST_EMPLACE_CODE(N) \
1309    BOOST_MOVE_TMPL_LT##N BOOST_MOVE_CLASS##N BOOST_MOVE_GT##N \
1310    iterator emplace(const_iterator p BOOST_MOVE_I##N BOOST_MOVE_UREF##N)\
1311    {\
1312       return this->emplace_after(this->previous(p) BOOST_MOVE_I##N BOOST_MOVE_FWD##N);\
1313    }\
1314    //
1315    BOOST_MOVE_ITERATE_0TO9(BOOST_CONTAINER_SLIST_EMPLACE_CODE)
1316    #undef BOOST_CONTAINER_SLIST_EMPLACE_CODE
1317 
1318    #endif   // !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
1319 
1320    #if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
1321    //! <b>Requires</b>: p must be a valid iterator of *this.
1322    //!
1323    //! <b>Effects</b>: Insert a copy of x before p.
1324    //!
1325    //! <b>Returns</b>: an iterator to the inserted element.
1326    //!
1327    //! <b>Throws</b>: If memory allocation throws or x's copy constructor throws.
1328    //!
1329    //! <b>Complexity</b>: Linear to the elements before p.
1330    iterator insert(const_iterator p, const T &x);
1331 
1332    //! <b>Requires</b>: p must be a valid iterator of *this.
1333    //!
1334    //! <b>Effects</b>: Insert a new element before p with x's resources.
1335    //!
1336    //! <b>Returns</b>: an iterator to the inserted element.
1337    //!
1338    //! <b>Throws</b>: If memory allocation throws.
1339    //!
1340    //! <b>Complexity</b>: Linear to the elements before p.
1341    iterator insert(const_iterator prev_p, T &&x);
1342    #else
1343    BOOST_MOVE_CONVERSION_AWARE_CATCH_1ARG(insert, T, iterator, priv_insert, const_iterator, const_iterator)
1344    #endif
1345 
1346    //! <b>Requires</b>: p must be a valid iterator of *this.
1347    //!
1348    //! <b>Effects</b>: Inserts n copies of x before p.
1349    //!
1350    //! <b>Returns</b>: an iterator to the first inserted element or p if n == 0.
1351    //!
1352    //! <b>Throws</b>: If memory allocation throws or T's copy constructor throws.
1353    //!
1354    //! <b>Complexity</b>: Linear to n plus linear to the elements before p.
1355    iterator insert(const_iterator p, size_type n, const value_type& x)
1356    {
1357       const_iterator prev(this->previous(p));
1358       this->insert_after(prev, n, x);
1359       return ++iterator(prev.get());
1360    }
1361 
1362    //! <b>Requires</b>: p must be a valid iterator of *this.
1363    //!
1364    //! <b>Effects</b>: Insert a copy of the [first, last) range before p.
1365    //!
1366    //! <b>Returns</b>: an iterator to the first inserted element or p if first == last.
1367    //!
1368    //! <b>Throws</b>: If memory allocation throws, T's constructor from a
1369    //!   dereferenced InpIt throws.
1370    //!
1371    //! <b>Complexity</b>: Linear to distance [first, last) plus
1372    //!    linear to the elements before p.
1373    template <class InIter>
1374    iterator insert(const_iterator p, InIter first, InIter last)
1375    {
1376       const_iterator prev(this->previous(p));
1377       this->insert_after(prev, first, last);
1378       return ++iterator(prev.get());
1379    }
1380 
1381 #if !defined(BOOST_NO_CXX11_HDR_INITIALIZER_LIST)
1382    //! <b>Requires</b>: p must be a valid iterator of *this.
1383    //!
1384    //! <b>Effects</b>: Insert a copy of the [il.begin(), il.end()) range before p.
1385    //!
1386    //! <b>Returns</b>: an iterator to the first inserted element or p if il.begin() == il.end().
1387    //!
1388    //! <b>Throws</b>: If memory allocation throws, T's constructor from a
1389    //!   dereferenced std::initializer_list iterator throws.
1390    //!
1391    //! <b>Complexity</b>: Linear to the range [il.begin(), il.end()) plus
1392    //!    linear to the elements before p.
1393    iterator insert(const_iterator p, std::initializer_list<value_type> il)
1394    {
1395        return insert(p, il.begin(), il.end());
1396    }
1397 #endif
1398 
1399    //! <b>Requires</b>: p must be a valid iterator of *this.
1400    //!
1401    //! <b>Effects</b>: Erases the element at p.
1402    //!
1403    //! <b>Throws</b>: Nothing.
1404    //!
1405    //! <b>Complexity</b>: Linear to the number of elements before p.
1406    iterator erase(const_iterator p) BOOST_NOEXCEPT_OR_NOTHROW
1407    {  return iterator(this->erase_after(previous(p))); }
1408 
1409    //! <b>Requires</b>: first and last must be valid iterator to elements in *this.
1410    //!
1411    //! <b>Effects</b>: Erases the elements pointed by [first, last).
1412    //!
1413    //! <b>Throws</b>: Nothing.
1414    //!
1415    //! <b>Complexity</b>: Linear to the distance between first and last plus
1416    //!   linear to the elements before first.
1417    iterator erase(const_iterator first, const_iterator last) BOOST_NOEXCEPT_OR_NOTHROW
1418    {  return iterator(this->erase_after(previous(first), last)); }
1419 
1420    //! <b>Requires</b>: p must point to an element contained
1421    //!   by the list. x != *this. this' allocator and x's allocator shall compare equal
1422    //!
1423    //! <b>Effects</b>: Transfers all the elements of list x to this list, before the
1424    //!   the element pointed by p. No destructors or copy constructors are called.
1425    //!
1426    //! <b>Throws</b>: Nothing
1427    //!
1428    //! <b>Complexity</b>: Linear in distance(begin(), p), and linear in x.size().
1429    //!
1430    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of
1431    //!    this list. Iterators of this list and all the references are not invalidated.
1432    void splice(const_iterator p, slist& x) BOOST_NOEXCEPT_OR_NOTHROW
1433    {  this->splice_after(this->previous(p), x);  }
1434 
1435    //! <b>Requires</b>: p must point to an element contained
1436    //!   by the list. x != *this. this' allocator and x's allocator shall compare equal
1437    //!
1438    //! <b>Effects</b>: Transfers all the elements of list x to this list, before the
1439    //!   the element pointed by p. No destructors or copy constructors are called.
1440    //!
1441    //! <b>Throws</b>: Nothing
1442    //!
1443    //! <b>Complexity</b>: Linear in distance(begin(), p), and linear in x.size().
1444    //!
1445    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of
1446    //!    this list. Iterators of this list and all the references are not invalidated.
1447    void splice(const_iterator p, BOOST_RV_REF(slist) x) BOOST_NOEXCEPT_OR_NOTHROW
1448    {  this->splice(p, BOOST_MOVE_TO_LV(x));  }
1449 
1450    //! <b>Requires</b>: p must point to an element contained
1451    //!   by this list. i must point to an element contained in list x.
1452    //!   this' allocator and x's allocator shall compare equal
1453    //!
1454    //! <b>Effects</b>: Transfers the value pointed by i, from list x to this list,
1455    //!   before the element pointed by p. No destructors or copy constructors are called.
1456    //!   If p == i or p == ++i, this function is a null operation.
1457    //!
1458    //! <b>Throws</b>: Nothing
1459    //!
1460    //! <b>Complexity</b>: Linear in distance(begin(), p), and in distance(x.begin(), i).
1461    //!
1462    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1463    //!   list. Iterators of this list and all the references are not invalidated.
1464    void splice(const_iterator p, slist& x, const_iterator i) BOOST_NOEXCEPT_OR_NOTHROW
1465    {  this->splice_after(this->previous(p), x, x.previous(i));  }
1466 
1467    //! <b>Requires</b>: p must point to an element contained
1468    //!   by this list. i must point to an element contained in list x.
1469    //!   this' allocator and x's allocator shall compare equal.
1470    //!
1471    //! <b>Effects</b>: Transfers the value pointed by i, from list x to this list,
1472    //!   before the element pointed by p. No destructors or copy constructors are called.
1473    //!   If p == i or p == ++i, this function is a null operation.
1474    //!
1475    //! <b>Throws</b>: Nothing
1476    //!
1477    //! <b>Complexity</b>: Linear in distance(begin(), p), and in distance(x.begin(), i).
1478    //!
1479    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1480    //!   list. Iterators of this list and all the references are not invalidated.
1481    void splice(const_iterator p, BOOST_RV_REF(slist) x, const_iterator i) BOOST_NOEXCEPT_OR_NOTHROW
1482    {  this->splice(p, BOOST_MOVE_TO_LV(x), i);  }
1483 
1484    //! <b>Requires</b>: p must point to an element contained
1485    //!   by this list. first and last must point to elements contained in list x.
1486    //!
1487    //! <b>Effects</b>: Transfers the range pointed by first and last from list x to this list,
1488    //!   before the element pointed by p. No destructors or copy constructors are called.
1489    //!   this' allocator and x's allocator shall compare equal.
1490    //!
1491    //! <b>Throws</b>: Nothing
1492    //!
1493    //! <b>Complexity</b>: Linear in distance(begin(), p), in distance(x.begin(), first),
1494    //!   and in distance(first, last).
1495    //!
1496    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1497    //!   list. Iterators of this list and all the references are not invalidated.
1498    void splice(const_iterator p, slist& x, const_iterator first, const_iterator last) BOOST_NOEXCEPT_OR_NOTHROW
1499    {  this->splice_after(this->previous(p), x, x.previous(first), x.previous(last));  }
1500 
1501    //! <b>Requires</b>: p must point to an element contained
1502    //!   by this list. first and last must point to elements contained in list x.
1503    //!   this' allocator and x's allocator shall compare equal
1504    //!
1505    //! <b>Effects</b>: Transfers the range pointed by first and last from list x to this list,
1506    //!   before the element pointed by p. No destructors or copy constructors are called.
1507    //!
1508    //! <b>Throws</b>: Nothing
1509    //!
1510    //! <b>Complexity</b>: Linear in distance(begin(), p), in distance(x.begin(), first),
1511    //!   and in distance(first, last).
1512    //!
1513    //! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
1514    //!   list. Iterators of this list and all the references are not invalidated.
1515    void splice(const_iterator p, BOOST_RV_REF(slist) x, const_iterator first, const_iterator last) BOOST_NOEXCEPT_OR_NOTHROW
1516    {  this->splice(p, BOOST_MOVE_TO_LV(x), first, last);  }
1517 
1518    //! <b>Effects</b>: Returns true if x and y are equal
1519    //!
1520    //! <b>Complexity</b>: Linear to the number of elements in the container.
1521    friend bool operator==(const slist& x, const slist& y)
1522    {  return x.size() == y.size() && ::boost::container::algo_equal(x.begin(), x.end(), y.begin());  }
1523 
1524    //! <b>Effects</b>: Returns true if x and y are unequal
1525    //!
1526    //! <b>Complexity</b>: Linear to the number of elements in the container.
1527    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
1528       friend bool operator!=(const slist& x, const slist& y)
1529    {  return !(x == y); }
1530 
1531    //! <b>Effects</b>: Returns true if x is less than y
1532    //!
1533    //! <b>Complexity</b>: Linear to the number of elements in the container.
1534    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
1535       friend bool operator<(const slist& x, const slist& y)
1536    {  return ::boost::container::algo_lexicographical_compare(x.begin(), x.end(), y.begin(), y.end());  }
1537 
1538    //! <b>Effects</b>: Returns true if x is greater than y
1539    //!
1540    //! <b>Complexity</b>: Linear to the number of elements in the container.
1541    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
1542       friend bool operator>(const slist& x, const slist& y)
1543    {  return y < x;  }
1544 
1545    //! <b>Effects</b>: Returns true if x is equal or less than y
1546    //!
1547    //! <b>Complexity</b>: Linear to the number of elements in the container.
1548    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
1549       friend bool operator<=(const slist& x, const slist& y)
1550    {  return !(y < x);  }
1551 
1552    //! <b>Effects</b>: Returns true if x is equal or greater than y
1553    //!
1554    //! <b>Complexity</b>: Linear to the number of elements in the container.
1555    BOOST_CONTAINER_ATTRIBUTE_NODISCARD inline
1556       friend bool operator>=(const slist& x, const slist& y)
1557    {  return !(x < y);  }
1558 
1559    //! <b>Effects</b>: x.swap(y)
1560    //!
1561    //! <b>Complexity</b>: Constant.
1562    friend void swap(slist& x, slist& y)
1563        BOOST_NOEXCEPT_IF(BOOST_NOEXCEPT(x.swap(y)))
1564    {  x.swap(y);  }
1565 
1566    #ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
1567    private:
1568    void priv_move_assign(BOOST_RV_REF(slist) x, dtl::bool_<true> /*steal_resources*/)
1569    {
1570       //Destroy objects but retain memory in case x reuses it in the future
1571       this->clear();
1572       //Move allocator if needed
1573       this->AllocHolder::move_assign_alloc(x);
1574       //Obtain resources
1575       this->icont() = boost::move(x.icont());
1576    }
1577 
1578    void priv_move_assign(BOOST_RV_REF(slist) x, dtl::bool_<false> /*steal_resources*/)
1579    {
1580       //We can't guarantee a compile-time equal allocator or propagation so fallback to runtime
1581       //Resources can be transferred if both allocators are equal
1582       if (this->node_alloc() == x.node_alloc()) {
1583          this->priv_move_assign(boost::move(x), dtl::true_());
1584       }
1585       else {
1586          this->assign(boost::make_move_iterator(x.begin()), boost::make_move_iterator(x.end()));
1587       }
1588    }
1589 
1590    template<class U>
1591    void priv_push_front(BOOST_FWD_REF(U) x)
1592    {  this->icont().push_front(*this->create_node(::boost::forward<U>(x))); }
1593 
1594    bool priv_try_shrink(size_type new_size, const_iterator &last_pos)
1595    {
1596       typename Icont::iterator end_n(this->icont().end()), cur(this->icont().before_begin()), cur_next;
1597       while (++(cur_next = cur) != end_n && new_size > 0){
1598          --new_size;
1599          cur = cur_next;
1600       }
1601       last_pos = const_iterator(cur);
1602       if (cur_next != end_n){
1603          this->erase_after(last_pos, const_iterator(end_n));
1604          return true;
1605       }
1606       else{
1607          return false;
1608       }
1609    }
1610 
1611    template<class U>
1612    iterator priv_insert(const_iterator p, BOOST_FWD_REF(U) x)
1613    {  return this->insert_after(previous(p), ::boost::forward<U>(x)); }
1614 
1615    template<class U>
1616    iterator priv_insert_after(const_iterator prev_p, BOOST_FWD_REF(U) x)
1617    {  return iterator(this->icont().insert_after(prev_p.get(), *this->create_node(::boost::forward<U>(x)))); }
1618 
1619    class insertion_functor;
1620    friend class insertion_functor;
1621 
1622    class insertion_functor
1623    {
1624       Icont &icont_;
1625       typedef typename Icont::iterator       iiterator;
1626       typedef typename Icont::const_iterator iconst_iterator;
1627       const iconst_iterator prev_;
1628       iiterator   ret_;
1629 
1630       public:
1631       insertion_functor(Icont &icont, typename Icont::const_iterator prev)
1632          :  icont_(icont), prev_(prev), ret_(prev.unconst())
1633       {}
1634 
1635       void operator()(Node &n)
1636       {
1637          ret_ = this->icont_.insert_after(prev_, n);
1638       }
1639 
1640       iiterator inserted_first() const
1641       {  return ret_;   }
1642    };
1643 
1644    //Functors for member algorithm defaults
1645    typedef value_less<value_type>   value_less_t;
1646    typedef value_equal<value_type>  value_equal_t;
1647 
1648    #endif   //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
1649 };
1650 
1651 #ifndef BOOST_CONTAINER_NO_CXX17_CTAD
1652 
1653 template <typename InpIt>
1654 slist(InpIt, InpIt) ->
1655    slist<typename iterator_traits<InpIt>::value_type>;
1656 
1657 template <typename InpIt, typename Allocator>
1658 slist(InpIt, InpIt, Allocator const&) ->
1659    slist<typename iterator_traits<InpIt>::value_type, Allocator>;
1660 
1661 #endif
1662 
1663 }}
1664 
1665 #ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
1666 
1667 namespace boost {
1668 
1669 //!has_trivial_destructor_after_move<> == true_type
1670 //!specialization for optimizations
1671 template <class T, class Allocator>
1672 struct has_trivial_destructor_after_move<boost::container::slist<T, Allocator> >
1673 {
1674    typedef typename boost::container::slist<T, Allocator>::allocator_type allocator_type;
1675    typedef typename ::boost::container::allocator_traits<allocator_type>::pointer pointer;
1676    BOOST_STATIC_CONSTEXPR bool value = ::boost::has_trivial_destructor_after_move<allocator_type>::value &&
1677                              ::boost::has_trivial_destructor_after_move<pointer>::value;
1678 };
1679 
1680 namespace container {
1681 
1682 }} //namespace boost{  namespace container {
1683 
1684 #endif   //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
1685 
1686 // Specialization of insert_iterator so that insertions will be constant
1687 // time rather than linear time.
1688 
1689 #include <boost/move/detail/std_ns_begin.hpp>
1690 BOOST_CONTAINER_DOC1ST(namespace std {, BOOST_MOVE_STD_NS_BEG)
1691 
1692 //! A specialization of insert_iterator
1693 //! that works with slist
1694 template <class T, class ValueAllocator>
1695 class insert_iterator<boost::container::slist<T, ValueAllocator> >
1696 {
1697    private:
1698    typedef boost::container::slist<T, ValueAllocator> Container;
1699    Container* container;
1700    typename Container::iterator iter;
1701 
1702    public:
1703    typedef Container           container_type;
1704    typedef output_iterator_tag iterator_category;
1705    typedef void                value_type;
1706    typedef void                difference_type;
1707    typedef void                pointer;
1708    typedef void                reference;
1709 
1710    insert_iterator(Container& x,
1711                    typename Container::iterator i,
1712                    bool is_previous = false)
1713       : container(&x), iter(is_previous ? i : x.previous(i)){ }
1714 
1715    insert_iterator<Container>&
1716       operator=(const typename Container::value_type& value)
1717    {
1718       iter = container->insert_after(iter, value);
1719       return *this;
1720    }
1721    insert_iterator<Container>& operator*(){ return *this; }
1722    insert_iterator<Container>& operator++(){ return *this; }
1723    insert_iterator<Container>& operator++(int){ return *this; }
1724 };
1725 
1726 BOOST_CONTAINER_DOC1ST( }, BOOST_MOVE_STD_NS_END)
1727 #include <boost/move/detail/std_ns_end.hpp>
1728 
1729 #include <boost/container/detail/config_end.hpp>
1730 
1731 #endif // BOOST_CONTAINER_SLIST_HPP