mirror of
https://github.com/boostorg/container.git
synced 2025-08-03 06:24:26 +02:00
Changes for 1.49
[SVN r76179]
This commit is contained in:
381
include/boost/container/allocator/allocator_traits.hpp
Normal file
381
include/boost/container/allocator/allocator_traits.hpp
Normal file
@@ -0,0 +1,381 @@
|
|||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// (C) Copyright Pablo Halpern 2009. Distributed under the Boost
|
||||||
|
// Software License, Version 1.0. (See accompanying file
|
||||||
|
// LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// (C) Copyright Ion Gaztanaga 2011-2011. Distributed under the Boost
|
||||||
|
// Software License, Version 1.0. (See accompanying file
|
||||||
|
// LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
//
|
||||||
|
// See http://www.boost.org/libs/container for documentation.
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
#ifndef BOOST_CONTAINER_ALLOCATOR_ALLOCATOR_TRAITS_HPP
|
||||||
|
#define BOOST_CONTAINER_ALLOCATOR_ALLOCATOR_TRAITS_HPP
|
||||||
|
|
||||||
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
|
# pragma once
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include <boost/container/detail/config_begin.hpp>
|
||||||
|
#include <boost/container/detail/workaround.hpp>
|
||||||
|
#include <boost/intrusive/pointer_traits.hpp>
|
||||||
|
#include <boost/container/allocator/memory_util.hpp>
|
||||||
|
#include <boost/type_traits/integral_constant.hpp>
|
||||||
|
#include <boost/move/move.hpp>
|
||||||
|
#include <limits> //numeric_limits<>::max()
|
||||||
|
#include <new> //placement new
|
||||||
|
#include <memory> //std::allocator
|
||||||
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
|
|
||||||
|
///@cond
|
||||||
|
|
||||||
|
namespace boost {
|
||||||
|
namespace container {
|
||||||
|
namespace container_detail {
|
||||||
|
|
||||||
|
//workaround needed for C++03 compilers with no construct()
|
||||||
|
//supporting rvalue references
|
||||||
|
template<class A>
|
||||||
|
struct is_std_allocator
|
||||||
|
{ static const bool value = false; };
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
struct is_std_allocator< std::allocator<T> >
|
||||||
|
{ static const bool value = true; };
|
||||||
|
|
||||||
|
} //namespace container_detail {
|
||||||
|
|
||||||
|
///@endcond
|
||||||
|
|
||||||
|
template <typename Alloc>
|
||||||
|
struct allocator_traits
|
||||||
|
{
|
||||||
|
//allocator_type
|
||||||
|
typedef Alloc allocator_type;
|
||||||
|
//value_type
|
||||||
|
typedef typename Alloc::value_type value_type;
|
||||||
|
|
||||||
|
#if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
//!Alloc::pointer if such a type exists; otherwise, value_type*
|
||||||
|
//!
|
||||||
|
typedef unspecified pointer;
|
||||||
|
//!Alloc::const_pointer if such a type exists ; otherwise, pointer_traits<pointer>::rebind<const
|
||||||
|
//!
|
||||||
|
typedef unspecified const_pointer;
|
||||||
|
//!Non-standard extension
|
||||||
|
//!Alloc::reference if such a type exists; otherwise, value_type&
|
||||||
|
typedef unspecified pointer;
|
||||||
|
//!Non-standard extension
|
||||||
|
//!Alloc::const_reference if such a type exists ; otherwise, const value_type&
|
||||||
|
typedef unspecified const_pointer;
|
||||||
|
//!Alloc::void_pointer if such a type exists ; otherwise, pointer_traits<pointer>::rebind<void>.
|
||||||
|
//!
|
||||||
|
typedef unspecified void_pointer;
|
||||||
|
//!Alloc::const_void_pointer if such a type exists ; otherwis e, pointer_traits<pointer>::rebind<const
|
||||||
|
//!
|
||||||
|
typedef unspecified const_void_pointer;
|
||||||
|
//!Alloc::difference_type if such a type exists ; otherwise, pointer_traits<pointer>::difference_type.
|
||||||
|
//!
|
||||||
|
typedef unspecified difference_type;
|
||||||
|
//!Alloc::size_type if such a type exists ; otherwise, make_unsigned<difference_type>::type
|
||||||
|
//!
|
||||||
|
typedef unspecified size_type;
|
||||||
|
//!Alloc::propagate_on_container_copy_assignment if such a type exists, otherwise an integral_constant
|
||||||
|
//!type with internal constant static member <pre>value</pre> == false.
|
||||||
|
typedef unspecified propagate_on_container_copy_assignment;
|
||||||
|
//!Alloc::propagate_on_container_move_assignment if such a type exists, otherwise an integral_constant
|
||||||
|
//!type with internal constant static member <pre>value</pre> == false.
|
||||||
|
typedef unspecified propagate_on_container_move_assignment;
|
||||||
|
//!Alloc::propagate_on_container_swap if such a type exists, otherwise an integral_constant
|
||||||
|
//!type with internal constant static member <pre>value</pre> == false.
|
||||||
|
typedef unspecified propagate_on_container_swap;
|
||||||
|
//!Defines an allocator: Alloc::rebind<T>::other if such a type exists; otherwise, Alloc<T, Args>
|
||||||
|
//!if Alloc is a class template instantiation of the form Alloc<U, Args>, where Args is zero or
|
||||||
|
//!more type arguments ; otherwise, the instantiation of rebind_alloc is ill-formed.
|
||||||
|
//!
|
||||||
|
//!In C++03 compilers <pre>rebind_alloc</pre> is a struct derived from an allocator
|
||||||
|
//!deduced by previously detailed rules.
|
||||||
|
template <class T> using rebind_alloc = unspecified;
|
||||||
|
|
||||||
|
//!In C++03 compilers <pre>rebind_traits</pre> is a struct derived from
|
||||||
|
//!<pre>allocator_traits<OtherAlloc><pre>, where `OtherAlloc` is
|
||||||
|
//!the allocator deduced by rules explained in `rebind_alloc`.
|
||||||
|
template <class T> using rebind_traits = allocator_traits<rebind_alloc<T> >;
|
||||||
|
|
||||||
|
//!Non-standard extension: Portable allocator rebind for C++03 and C++11 compilers.
|
||||||
|
//!`type` is an allocator related to Alloc deduced deduced by rules explained in `rebind_alloc`.
|
||||||
|
template <class T>
|
||||||
|
struct portable_rebind_alloc
|
||||||
|
{ typedef unspecified_type type; };
|
||||||
|
#else
|
||||||
|
//pointer
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
pointer, value_type*)
|
||||||
|
pointer;
|
||||||
|
//const_pointer
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
const_pointer, typename boost::intrusive::pointer_traits<pointer>::template
|
||||||
|
rebind_pointer<const value_type>::type)
|
||||||
|
const_pointer;
|
||||||
|
//reference
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
reference, value_type&)
|
||||||
|
reference;
|
||||||
|
//const_reference
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
const_reference, const value_type&)
|
||||||
|
const_reference;
|
||||||
|
//void_pointer
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
void_pointer, typename boost::intrusive::pointer_traits<pointer>::template
|
||||||
|
rebind_pointer<void>::type)
|
||||||
|
void_pointer;
|
||||||
|
//const_void_pointer
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
const_void_pointer, typename boost::intrusive::pointer_traits<pointer>::template
|
||||||
|
rebind_pointer<const void>::type)
|
||||||
|
const_void_pointer;
|
||||||
|
//difference_type
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
difference_type, std::ptrdiff_t)
|
||||||
|
difference_type;
|
||||||
|
//size_type
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
size_type, std::size_t)
|
||||||
|
size_type;
|
||||||
|
//propagate_on_container_copy_assignment
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
propagate_on_container_copy_assignment, boost::false_type)
|
||||||
|
propagate_on_container_copy_assignment;
|
||||||
|
//propagate_on_container_move_assignment
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
propagate_on_container_move_assignment, boost::false_type)
|
||||||
|
propagate_on_container_move_assignment;
|
||||||
|
//propagate_on_container_swap
|
||||||
|
typedef BOOST_INTRUSIVE_OBTAIN_TYPE_WITH_DEFAULT(boost::container::container_detail::, Alloc,
|
||||||
|
propagate_on_container_swap, boost::false_type)
|
||||||
|
propagate_on_container_swap;
|
||||||
|
|
||||||
|
#if !defined(BOOST_NO_TEMPLATE_ALIASES)
|
||||||
|
//C++11
|
||||||
|
template <typename T> using rebind_alloc = boost::intrusive::detail::type_rebinder<Alloc, T>::type;
|
||||||
|
template <typename T> using rebind_traits = allocator_traits< rebind_alloc<T> >;
|
||||||
|
#else //!defined(BOOST_NO_TEMPLATE_ALIASES)
|
||||||
|
//Some workaround for C++03 or C++11 compilers with no template aliases
|
||||||
|
template <typename T>
|
||||||
|
struct rebind_alloc : boost::intrusive::detail::type_rebinder<Alloc,T>::type
|
||||||
|
{
|
||||||
|
typedef typename boost::intrusive::detail::type_rebinder<Alloc,T>::type Base;
|
||||||
|
#if !defined(BOOST_NO_VARIADIC_TEMPLATES)
|
||||||
|
template <typename... Args>
|
||||||
|
rebind_alloc(Args&&... args)
|
||||||
|
: Base(boost::forward<Args>(args)...)
|
||||||
|
{}
|
||||||
|
#else //!defined(BOOST_NO_VARIADIC_TEMPLATES)
|
||||||
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
rebind_alloc(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
|
: Base(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)) \
|
||||||
|
{} \
|
||||||
|
//
|
||||||
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
#endif //!defined(BOOST_NO_VARIADIC_TEMPLATES)
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
struct rebind_traits
|
||||||
|
: allocator_traits<typename boost::intrusive::detail::type_rebinder<Alloc, T>::type>
|
||||||
|
{};
|
||||||
|
#endif //!defined(BOOST_NO_TEMPLATE_ALIASES)
|
||||||
|
template <class T>
|
||||||
|
struct portable_rebind_alloc
|
||||||
|
{ typedef typename boost::intrusive::detail::type_rebinder<Alloc, T>::type type; };
|
||||||
|
#endif //BOOST_CONTAINER_DOXYGEN_INVOKED
|
||||||
|
|
||||||
|
//!<b>Returns</b>: a.allocate(n)
|
||||||
|
//!
|
||||||
|
static pointer allocate(Alloc &a, size_type n)
|
||||||
|
{ return a.allocate(n); }
|
||||||
|
|
||||||
|
//!<b>Returns</b>: a.deallocate(p, n)
|
||||||
|
//!
|
||||||
|
//!<b>Throws</b>: Nothing
|
||||||
|
static void deallocate(Alloc &a, pointer p, size_type n)
|
||||||
|
{ return a.deallocate(p, n); }
|
||||||
|
|
||||||
|
//!<b>Effects</b>: calls `a.construct(p, std::forward<Args>(args)...)` if that call is well-formed;
|
||||||
|
//!otherwise, invokes `::new (static_cast<void*>(p)) T(std::forward<Args>(args)...)`
|
||||||
|
static pointer allocate(Alloc &a, size_type n, const_void_pointer p)
|
||||||
|
{
|
||||||
|
const bool value = boost::container::container_detail::
|
||||||
|
has_member_function_callable_with_allocate
|
||||||
|
<Alloc, const size_type, const const_void_pointer>::value;
|
||||||
|
::boost::integral_constant<bool, value> flag;
|
||||||
|
return allocator_traits::priv_allocate(flag, a, n, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
//!<b>Effects</b>: calls a.destroy(p) if that call is well-formed;
|
||||||
|
//!otherwise, invokes `p->~T()`.
|
||||||
|
template<class T>
|
||||||
|
static void destroy(Alloc &a, T*p)
|
||||||
|
{
|
||||||
|
typedef T* destroy_pointer;
|
||||||
|
const bool value = boost::container::container_detail::
|
||||||
|
has_member_function_callable_with_destroy
|
||||||
|
<Alloc, const destroy_pointer>::value;
|
||||||
|
::boost::integral_constant<bool, value> flag;
|
||||||
|
allocator_traits::priv_destroy(flag, a, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
//!<b>Returns</b>: a.max_size() if that expression is well-formed; otherwise,
|
||||||
|
//!`numeric_limits<size_type>::max()`.
|
||||||
|
static size_type max_size(const Alloc &a)
|
||||||
|
{
|
||||||
|
const bool value = boost::container::container_detail::
|
||||||
|
has_member_function_callable_with_max_size
|
||||||
|
<const Alloc>::value;
|
||||||
|
::boost::integral_constant<bool, value> flag;
|
||||||
|
return allocator_traits::priv_max_size(flag, a);
|
||||||
|
}
|
||||||
|
|
||||||
|
//!<b>Returns</b>: a.select_on_container_copy_construction() if that expres sion is well- formed;
|
||||||
|
//!otherwise, a.
|
||||||
|
static Alloc select_on_container_copy_construction(const Alloc &a)
|
||||||
|
{
|
||||||
|
const bool value = boost::container::container_detail::
|
||||||
|
has_member_function_callable_with_select_on_container_copy_construction
|
||||||
|
<const Alloc>::value;
|
||||||
|
::boost::integral_constant<bool, value> flag;
|
||||||
|
return allocator_traits::priv_select_on_container_copy_construction(flag, a);
|
||||||
|
}
|
||||||
|
|
||||||
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
//!Effects: calls a.construct(p, std::forward<Args>(args)...) if that call is well-formed;
|
||||||
|
//!otherwise, invokes `::new (static_cast<void*>(p)) T(std::forward<Args>(args)...)`
|
||||||
|
template <class T, class ...Args>
|
||||||
|
static void construct(Alloc & a, T* p, Args&&... args)
|
||||||
|
{
|
||||||
|
::boost::integral_constant<bool, container_detail::is_std_allocator<Alloc>::value> flag;
|
||||||
|
allocator_traits::priv_construct(flag, a, p, ::boost::forward<Args>(args)...);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if !defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
private:
|
||||||
|
static pointer priv_allocate(boost::true_type, Alloc &a, size_type n, const_void_pointer p)
|
||||||
|
{ return a.allocate(n, p); }
|
||||||
|
|
||||||
|
static pointer priv_allocate(boost::false_type, Alloc &a, size_type n, const_void_pointer)
|
||||||
|
{ return allocator_traits::allocate(a, n); }
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
static void priv_destroy(boost::true_type, Alloc &a, T* p)
|
||||||
|
{ a.destroy(p); }
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
static void priv_destroy(boost::false_type, Alloc &, T* p)
|
||||||
|
{ p->~T(); (void)p; }
|
||||||
|
|
||||||
|
static size_type priv_max_size(boost::true_type, const Alloc &a)
|
||||||
|
{ return a.max_size(); }
|
||||||
|
|
||||||
|
static size_type priv_max_size(boost::false_type, const Alloc &)
|
||||||
|
{ return (std::numeric_limits<size_type>::max)(); }
|
||||||
|
|
||||||
|
static Alloc priv_select_on_container_copy_construction(boost::true_type, const Alloc &a)
|
||||||
|
{ return a.select_on_container_copy_construction(); }
|
||||||
|
|
||||||
|
static Alloc priv_select_on_container_copy_construction(boost::false_type, const Alloc &a)
|
||||||
|
{ return a; }
|
||||||
|
|
||||||
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING)
|
||||||
|
template<class T, class ...Args>
|
||||||
|
static void priv_construct(boost::false_type, Alloc &a, T *p, Args && ...args)
|
||||||
|
{
|
||||||
|
const bool value = boost::container::container_detail::
|
||||||
|
has_member_function_callable_with_construct
|
||||||
|
< Alloc, T*, Args... >::value;
|
||||||
|
::boost::integral_constant<bool, value> flag;
|
||||||
|
priv_construct_dispatch2(flag, a, p, ::boost::forward<Args>(args)...);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class T, class ...Args>
|
||||||
|
static void priv_construct(boost::true_type, Alloc &a, T *p, Args && ...args)
|
||||||
|
{
|
||||||
|
priv_construct_dispatch2(boost::false_type(), a, p, ::boost::forward<Args>(args)...);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class T, class ...Args>
|
||||||
|
static void priv_construct_dispatch2(boost::true_type, Alloc &a, T *p, Args && ...args)
|
||||||
|
{ a.construct( p, ::boost::forward<Args>(args)...); }
|
||||||
|
|
||||||
|
template<class T, class ...Args>
|
||||||
|
static void priv_construct_dispatch2(boost::false_type, Alloc &, T *p, Args && ...args)
|
||||||
|
{ ::new((void*)p) T(::boost::forward<Args>(args)...); }
|
||||||
|
#else
|
||||||
|
public:
|
||||||
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
|
template<class T BOOST_PP_ENUM_TRAILING_PARAMS(n, class P) > \
|
||||||
|
static void construct(Alloc &a, T *p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
|
{ \
|
||||||
|
::boost::integral_constant<bool, container_detail::is_std_allocator<Alloc>::value> flag; \
|
||||||
|
allocator_traits::priv_construct(flag, a, p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); \
|
||||||
|
} \
|
||||||
|
//
|
||||||
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
|
private:
|
||||||
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
|
template<class T BOOST_PP_ENUM_TRAILING_PARAMS(n, class P) > \
|
||||||
|
static void priv_construct(boost::false_type, Alloc &a, T *p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST,_)) \
|
||||||
|
{ \
|
||||||
|
const bool value = \
|
||||||
|
boost::container::container_detail::has_member_function_callable_with_construct \
|
||||||
|
< Alloc, T* BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_FWD_TYPE, _) >::value; \
|
||||||
|
::boost::integral_constant<bool, value> flag; \
|
||||||
|
priv_construct_dispatch2(flag, a, p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) ); \
|
||||||
|
} \
|
||||||
|
\
|
||||||
|
template<class T BOOST_PP_ENUM_TRAILING_PARAMS(n, class P) > \
|
||||||
|
static void priv_construct(boost::true_type, Alloc &a, T *p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST,_)) \
|
||||||
|
{ \
|
||||||
|
priv_construct_dispatch2(boost::false_type(), a, p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) ); \
|
||||||
|
} \
|
||||||
|
\
|
||||||
|
template<class T BOOST_PP_ENUM_TRAILING_PARAMS(n, class P) > \
|
||||||
|
static void priv_construct_dispatch2(boost::true_type, Alloc &a, T *p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST,_)) \
|
||||||
|
{ a.construct( p BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) ); } \
|
||||||
|
\
|
||||||
|
template<class T BOOST_PP_ENUM_TRAILING_PARAMS(n, class P) > \
|
||||||
|
static void priv_construct_dispatch2(boost::false_type, Alloc &, T *p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _) ) \
|
||||||
|
{ ::new((void*)p) T(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
|
//
|
||||||
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
#endif //BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
#endif //#if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
|
///@endcond
|
||||||
|
};
|
||||||
|
|
||||||
|
} //namespace container {
|
||||||
|
} //namespace boost {
|
||||||
|
|
||||||
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
|
#endif // ! defined(BOOST_CONTAINER_ALLOCATOR_ALLOCATOR_TRAITS_HPP)
|
77
include/boost/container/allocator/memory_util.hpp
Normal file
77
include/boost/container/allocator/memory_util.hpp
Normal file
@@ -0,0 +1,77 @@
|
|||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// (C) Copyright Ion Gaztanaga 2011-2011. Distributed under the Boost
|
||||||
|
// Software License, Version 1.0. (See accompanying file
|
||||||
|
// LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
//
|
||||||
|
// See http://www.boost.org/libs/container for documentation.
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
#ifndef BOOST_CONTAINER_ALLOCATOR_MEMORY_UTIL_HPP
|
||||||
|
#define BOOST_CONTAINER_ALLOCATOR_MEMORY_UTIL_HPP
|
||||||
|
|
||||||
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
|
# pragma once
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include <boost/container/detail/config_begin.hpp>
|
||||||
|
#include <boost/container/detail/workaround.hpp>
|
||||||
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
|
#include <boost/intrusive/detail/has_member_function_callable_with.hpp>
|
||||||
|
|
||||||
|
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME allocate
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEGIN namespace boost { namespace container { namespace container_detail {
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END }}}
|
||||||
|
#define BOOST_PP_ITERATION_PARAMS_1 (3, (0, 2, <boost/intrusive/detail/has_member_function_callable_with.hpp>))
|
||||||
|
#include BOOST_PP_ITERATE()
|
||||||
|
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME destroy
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEGIN namespace boost { namespace container { namespace container_detail {
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END }}}
|
||||||
|
#define BOOST_PP_ITERATION_PARAMS_1 (3, (0, 3, <boost/intrusive/detail/has_member_function_callable_with.hpp>))
|
||||||
|
#include BOOST_PP_ITERATE()
|
||||||
|
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME max_size
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEGIN namespace boost { namespace container { namespace container_detail {
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END }}}
|
||||||
|
#define BOOST_PP_ITERATION_PARAMS_1 (3, (0, 0, <boost/intrusive/detail/has_member_function_callable_with.hpp>))
|
||||||
|
#include BOOST_PP_ITERATE()
|
||||||
|
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME select_on_container_copy_construction
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEGIN namespace boost { namespace container { namespace container_detail {
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END }}}
|
||||||
|
#define BOOST_PP_ITERATION_PARAMS_1 (3, (0, 0, <boost/intrusive/detail/has_member_function_callable_with.hpp>))
|
||||||
|
#include BOOST_PP_ITERATE()
|
||||||
|
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME construct
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEGIN namespace boost { namespace container { namespace container_detail {
|
||||||
|
#define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END }}}
|
||||||
|
#define BOOST_PP_ITERATION_PARAMS_1 (3, (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS+1, <boost/intrusive/detail/has_member_function_callable_with.hpp>))
|
||||||
|
#include BOOST_PP_ITERATE()
|
||||||
|
|
||||||
|
namespace boost {
|
||||||
|
namespace container {
|
||||||
|
namespace container_detail {
|
||||||
|
|
||||||
|
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(pointer);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(const_pointer);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(reference);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(const_reference);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(void_pointer);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(const_void_pointer);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(size_type);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(propagate_on_container_copy_assignment);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(propagate_on_container_move_assignment);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(propagate_on_container_swap);
|
||||||
|
BOOST_INTRUSIVE_INSTANTIATE_DEFAULT_TYPE_TMPLT(difference_type);
|
||||||
|
|
||||||
|
} //namespace container_detail {
|
||||||
|
} //namespace container {
|
||||||
|
} //namespace boost {
|
||||||
|
|
||||||
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
|
#endif // ! defined(BOOST_CONTAINER_ALLOCATOR_MEMORY_UTIL_HPP)
|
651
include/boost/container/allocator/scoped_allocator.hpp
Normal file
651
include/boost/container/allocator/scoped_allocator.hpp
Normal file
@@ -0,0 +1,651 @@
|
|||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// (C) Copyright Pablo Halpern 2009. Distributed under the Boost
|
||||||
|
// Software License, Version 1.0. (See accompanying file
|
||||||
|
// LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// (C) Copyright Ion Gaztanaga 2011-2011. Distributed under the Boost
|
||||||
|
// Software License, Version 1.0. (See accompanying file
|
||||||
|
// LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
//
|
||||||
|
// See http://www.boost.org/libs/container for documentation.
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
#ifndef BOOST_CONTAINER_ALLOCATOR_SCOPED_ALLOCATOR_HPP
|
||||||
|
#define BOOST_CONTAINER_ALLOCATOR_SCOPED_ALLOCATOR_HPP
|
||||||
|
|
||||||
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
|
# pragma once
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include <boost/container/detail/config_begin.hpp>
|
||||||
|
#include <boost/container/detail/workaround.hpp>
|
||||||
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
|
#include <boost/type_traits.hpp>
|
||||||
|
#include <utility>
|
||||||
|
|
||||||
|
namespace boost { namespace container {
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
class scoped_allocator_adaptor;
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...> make_scoped();
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
class scoped_allocator_adaptor_base : public OuterAlloc
|
||||||
|
{
|
||||||
|
typedef allocator_traits<OuterAlloc> OuterTraits;
|
||||||
|
|
||||||
|
public:
|
||||||
|
// Workaround for inability of gcc-4.4.1 to expand InnerAllocs...
|
||||||
|
// typedef scoped_allocator_adaptor<InnerAllocs...> inner_allocator_type;
|
||||||
|
typedef decltype(make_scoped<InnerAllocs...>()) inner_allocator_type;
|
||||||
|
|
||||||
|
scoped_allocator_adaptor_base();
|
||||||
|
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base(OuterA2&& outerAlloc, const InnerAllocs&... innerAllocs);
|
||||||
|
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base(const scoped_allocator_adaptor<OuterA2, InnerAllocs...>& other);
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base(scoped_allocator_adaptor<OuterA2, InnerAllocs...>&& other);
|
||||||
|
|
||||||
|
inner_allocator_type& inner_allocator()
|
||||||
|
{ return _M_inner_allocs; }
|
||||||
|
inner_allocator_type const& inner_allocator() const
|
||||||
|
{ return _M_inner_allocs; }
|
||||||
|
|
||||||
|
// Allocator propagation functions.
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>
|
||||||
|
select_on_container_copy_construction() const;
|
||||||
|
|
||||||
|
typedef std::integral_constant<
|
||||||
|
bool,
|
||||||
|
OuterTraits::propagate_on_container_copy_assignment::value ||
|
||||||
|
inner_allocator_type::propagate_on_container_copy_assignment::value
|
||||||
|
> propagate_on_container_copy_assignment;
|
||||||
|
typedef std::integral_constant<
|
||||||
|
bool,
|
||||||
|
OuterTraits::propagate_on_container_move_assignment::value ||
|
||||||
|
inner_allocator_type::propagate_on_container_move_assignment::value
|
||||||
|
> propagate_on_container_move_assignment;
|
||||||
|
typedef std::integral_constant<
|
||||||
|
bool,
|
||||||
|
OuterTraits::propagate_on_container_swap::value ||
|
||||||
|
inner_allocator_type::propagate_on_container_swap::value
|
||||||
|
> propagate_on_container_swap;
|
||||||
|
|
||||||
|
private:
|
||||||
|
inner_allocator_type _M_inner_allocs;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Specialization with only one parameter.
|
||||||
|
template <typename OuterAlloc>
|
||||||
|
class scoped_allocator_adaptor_base<OuterAlloc> : public OuterAlloc
|
||||||
|
{
|
||||||
|
typedef allocator_traits<OuterAlloc> OuterTraits;
|
||||||
|
public:
|
||||||
|
typedef scoped_allocator_adaptor<OuterAlloc> inner_allocator_type;
|
||||||
|
|
||||||
|
scoped_allocator_adaptor_base();
|
||||||
|
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base(OuterA2&& outerAlloc);
|
||||||
|
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base(const scoped_allocator_adaptor<OuterA2>& other);
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base(scoped_allocator_adaptor<OuterA2>&& other);
|
||||||
|
|
||||||
|
inner_allocator_type& inner_allocator()
|
||||||
|
{ return static_cast<inner_allocator_type&>(*this); }
|
||||||
|
|
||||||
|
inner_allocator_type const& inner_allocator() const
|
||||||
|
{ return static_cast<const inner_allocator_type&>(*this); }
|
||||||
|
|
||||||
|
// Allocator propagation functions.
|
||||||
|
scoped_allocator_adaptor<OuterAlloc>
|
||||||
|
select_on_container_copy_construction() const;
|
||||||
|
|
||||||
|
typedef typename OuterTraits::propagate_on_container_copy_assignment propagate_on_container_copy_assignment;
|
||||||
|
typedef typename OuterTraits::propagate_on_container_move_assignment propagate_on_container_move_assignment;
|
||||||
|
typedef typename OuterTraits::propagate_on_container_swap propagate_on_container_swap;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
class scoped_allocator_adaptor
|
||||||
|
: public scoped_allocator_adaptor_base<OuterAlloc, InnerAllocs...>
|
||||||
|
{
|
||||||
|
typedef scoped_allocator_adaptor_base<OuterAlloc, InnerAllocs...> _Base;
|
||||||
|
typedef allocator_traits<OuterAlloc> _Traits;
|
||||||
|
|
||||||
|
public:
|
||||||
|
typedef OuterAlloc outer_allocator_type;
|
||||||
|
typedef typename _Base::inner_allocator_type inner_allocator_type;
|
||||||
|
|
||||||
|
typedef typename allocator_traits<OuterAlloc>::size_type size_type;
|
||||||
|
typedef typename allocator_traits<OuterAlloc>::difference_type difference_type;
|
||||||
|
typedef typename allocator_traits<OuterAlloc>::pointer pointer;
|
||||||
|
typedef typename allocator_traits<OuterAlloc>::const_pointer const_pointer;
|
||||||
|
typedef typename allocator_traits<OuterAlloc>::void_pointer void_pointer;
|
||||||
|
typedef typename allocator_traits<OuterAlloc>::const_void_pointer const_void_pointer;
|
||||||
|
typedef typename allocator_traits<OuterAlloc>::value_type value_type;
|
||||||
|
|
||||||
|
template <typename Tp>
|
||||||
|
struct rebind {
|
||||||
|
typedef typename allocator_traits<OuterAlloc>::template rebind_traits<Tp> rebound_traits;
|
||||||
|
typedef typename rebound_traits::allocator_type rebound_outer; // exposition only
|
||||||
|
typedef scoped_allocator_adaptor<rebound_outer, InnerAllocs...> other;
|
||||||
|
};
|
||||||
|
|
||||||
|
scoped_allocator_adaptor();
|
||||||
|
scoped_allocator_adaptor(const scoped_allocator_adaptor& other);
|
||||||
|
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor(const scoped_allocator_adaptor<OuterA2, InnerAllocs...>& other);
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor(scoped_allocator_adaptor<OuterA2, InnerAllocs...>&& other);
|
||||||
|
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor(OuterA2&& outerAlloc, const InnerAllocs&... innerAllocs);
|
||||||
|
|
||||||
|
~scoped_allocator_adaptor();
|
||||||
|
|
||||||
|
inner_allocator_type & inner_allocator()
|
||||||
|
{ return _Base::inner_allocator(); }
|
||||||
|
inner_allocator_type const& inner_allocator() const
|
||||||
|
{ return _Base::inner_allocator(); }
|
||||||
|
outer_allocator_type & outer_allocator()
|
||||||
|
{ return *this; }
|
||||||
|
outer_allocator_type const& outer_allocator() const
|
||||||
|
{ return *this; }
|
||||||
|
|
||||||
|
pointer allocate(size_type n);
|
||||||
|
pointer allocate(size_type n, const_void_pointer hint);
|
||||||
|
void deallocate(pointer p, size_type n);
|
||||||
|
size_type max_size() const;
|
||||||
|
|
||||||
|
template <typename T, typename... Args>
|
||||||
|
void construct(T* p, Args&&... args);
|
||||||
|
|
||||||
|
// Specializations to pass inner_allocator to pair::first and pair::second
|
||||||
|
template <class T1, class T2>
|
||||||
|
void construct(std::pair<T1,T2>* p);
|
||||||
|
template <class T1, class T2, class U, class V>
|
||||||
|
void construct(std::pair<T1,T2>* p, U&& x, V&& y);
|
||||||
|
template <class T1, class T2, class U, class V>
|
||||||
|
void construct(std::pair<T1,T2>* p, const std::pair<U, V>& pr);
|
||||||
|
template <class T1, class T2, class U, class V>
|
||||||
|
void construct(std::pair<T1,T2>* p, std::pair<U, V>&& pr);
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
void destroy(T* p);
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename OuterA1, typename OuterA2, typename... InnerAllocs>
|
||||||
|
inline
|
||||||
|
bool operator==(const scoped_allocator_adaptor<OuterA1,InnerAllocs...>& a,
|
||||||
|
const scoped_allocator_adaptor<OuterA2,InnerAllocs...>& b);
|
||||||
|
|
||||||
|
template <typename OuterA1, typename OuterA2, typename... InnerAllocs>
|
||||||
|
inline
|
||||||
|
bool operator!=(const scoped_allocator_adaptor<OuterA1,InnerAllocs...>& a,
|
||||||
|
const scoped_allocator_adaptor<OuterA2,InnerAllocs...>& b);
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Implementation of scoped_allocator_adaptor_base<OuterAlloc, InnerAllocs...>
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
inline
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor_base()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor_base(OuterA2&& outerAlloc,
|
||||||
|
const InnerAllocs&... innerAllocs)
|
||||||
|
: OuterAlloc(std::forward<OuterA2>(outerAlloc))
|
||||||
|
, _M_inner_allocs(innerAllocs...)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor_base(
|
||||||
|
const scoped_allocator_adaptor<OuterA2, InnerAllocs...>& other)
|
||||||
|
: OuterAlloc(other.outer_allocator())
|
||||||
|
, _M_inner_allocs(other.inner_allocator())
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor_base(
|
||||||
|
scoped_allocator_adaptor<OuterA2, InnerAllocs...>&& other)
|
||||||
|
: OuterAlloc(std::move(other.outer_allocator()))
|
||||||
|
, _M_inner_allocs(std::move(other.inner_allocator()))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
inline
|
||||||
|
scoped_allocator_adaptor<OuterAlloc,InnerAllocs...>
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc,InnerAllocs...>::
|
||||||
|
select_on_container_copy_construction() const
|
||||||
|
{
|
||||||
|
return scoped_allocator_adaptor<OuterAlloc,InnerAllocs...>(
|
||||||
|
allocator_traits<OuterAlloc>::select_on_container_copy_construction(
|
||||||
|
this->outer_allocator()),
|
||||||
|
allocator_traits<inner_allocator_type>::select_on_container_copy_construction(
|
||||||
|
this->inner_allocator()));
|
||||||
|
}
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Implementation of scoped_allocator_adaptor_base<OuterAlloc> specialization
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
template <typename OuterAlloc>
|
||||||
|
inline
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc>::
|
||||||
|
scoped_allocator_adaptor_base()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc>::
|
||||||
|
scoped_allocator_adaptor_base(OuterA2&& outerAlloc)
|
||||||
|
: OuterAlloc(std::forward<OuterA2>(outerAlloc))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc>::
|
||||||
|
scoped_allocator_adaptor_base(
|
||||||
|
const scoped_allocator_adaptor<OuterA2>& other)
|
||||||
|
: OuterAlloc(other.outer_allocator())
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc>::
|
||||||
|
scoped_allocator_adaptor_base(
|
||||||
|
scoped_allocator_adaptor<OuterA2>&& other)
|
||||||
|
: OuterAlloc(std::move(other.outer_allocator()))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
// template <typename OuterAlloc>
|
||||||
|
// inline
|
||||||
|
// scoped_allocator_adaptor<OuterAlloc>&
|
||||||
|
// scoped_allocator_adaptor_base<OuterAlloc>::inner_allocator()
|
||||||
|
// {
|
||||||
|
// return *this;
|
||||||
|
// }
|
||||||
|
|
||||||
|
// template <typename OuterAlloc>
|
||||||
|
// inline
|
||||||
|
// scoped_allocator_adaptor<OuterAlloc> const&
|
||||||
|
// scoped_allocator_adaptor_base<OuterAlloc>::inner_allocator() cosnt
|
||||||
|
// {
|
||||||
|
// return *this;
|
||||||
|
// }
|
||||||
|
|
||||||
|
template <typename OuterAlloc>
|
||||||
|
inline
|
||||||
|
scoped_allocator_adaptor<OuterAlloc>
|
||||||
|
scoped_allocator_adaptor_base<OuterAlloc>::
|
||||||
|
select_on_container_copy_construction() const
|
||||||
|
{
|
||||||
|
return
|
||||||
|
allocator_traits<OuterAlloc>::select_on_container_copy_construction(
|
||||||
|
this->outer_allocator());
|
||||||
|
}
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Implementation of scoped_allocator_adaptor details
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
namespace __details {
|
||||||
|
|
||||||
|
// Overload resolution for __has_ctor resolves to this function
|
||||||
|
// when _Tp is constructible with _Args. Returns true_type().
|
||||||
|
|
||||||
|
static void* __void_p; // Declared but not defined
|
||||||
|
|
||||||
|
template <typename _Tp, typename... _Args>
|
||||||
|
inline
|
||||||
|
auto __has_ctor(int, _Args&&... __args) ->
|
||||||
|
decltype((new (__void_p) _Tp(__args...), std::true_type()))
|
||||||
|
{ return std::true_type(); }
|
||||||
|
|
||||||
|
// Overload resolution for __has_ctor resolves to this function
|
||||||
|
// when _Tp is not constructible with _Args. Returns false_type().
|
||||||
|
template <typename _Tp, typename... _Args>
|
||||||
|
auto __has_ctor(_LowPriorityConversion<int>, _Args&&...) ->
|
||||||
|
std::false_type
|
||||||
|
{ return std::false_type(); }
|
||||||
|
|
||||||
|
template <typename _Alloc>
|
||||||
|
struct __is_scoped_allocator_imp {
|
||||||
|
template <typename T>
|
||||||
|
static char test(int, typename T::outer_allocator_type*);
|
||||||
|
template <typename T>
|
||||||
|
static int test(_LowPriorityConversion<int>, void*);
|
||||||
|
static const bool value = (1 == sizeof(test<_Alloc>(0, 0)));
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename _Alloc>
|
||||||
|
struct __is_scoped_allocator
|
||||||
|
: std::integral_constant<bool, __is_scoped_allocator_imp<_Alloc>::value>
|
||||||
|
{
|
||||||
|
};
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
// Called when outer_allocator_type is not a scoped allocator
|
||||||
|
// (recursion stop).
|
||||||
|
template <typename _Alloc>
|
||||||
|
inline
|
||||||
|
auto __outermost_alloc(_LowPriorityConversion<int>, _Alloc& __a) ->
|
||||||
|
_Alloc&
|
||||||
|
{
|
||||||
|
return __a;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Called when outer_allocator_type is a scoped allocator to
|
||||||
|
// return the outermost allocator type.
|
||||||
|
template <typename _Alloc>
|
||||||
|
inline auto __outermost_alloc(int, _Alloc& __a) ->
|
||||||
|
decltype(__outermost_alloc(0,__a.outer_allocator()))
|
||||||
|
{
|
||||||
|
return __a.outer_allocator();
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
template <typename _Ignore, typename _OuterAlloc,
|
||||||
|
typename _InnerAlloc, typename _Tp, typename... _Args>
|
||||||
|
inline void __dispatch_scoped_construct(std::false_type __uses_alloc,
|
||||||
|
_Ignore __use_alloc_prefix,
|
||||||
|
_OuterAlloc& __outer_alloc,
|
||||||
|
_InnerAlloc& __inner_alloc,
|
||||||
|
_Tp* __p, _Args&&... __args)
|
||||||
|
{
|
||||||
|
// _Tp doesn't use allocators. Construct without an
|
||||||
|
// allocator argument.
|
||||||
|
allocator_traits<_OuterAlloc>::construct(__outer_alloc, __p,
|
||||||
|
std::forward<_Args>(__args)...);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename _OuterAlloc,
|
||||||
|
typename _InnerAlloc, typename _Tp, typename... _Args>
|
||||||
|
inline void __dispatch_scoped_construct(std::true_type __uses_alloc,
|
||||||
|
std::true_type __use_alloc_prefix,
|
||||||
|
_OuterAlloc& __outer_alloc,
|
||||||
|
_InnerAlloc& __inner_alloc,
|
||||||
|
_Tp* __p, _Args&&... __args)
|
||||||
|
{
|
||||||
|
// _Tp doesn't use allocators. Construct without an
|
||||||
|
// allocator argument.
|
||||||
|
allocator_traits<_OuterAlloc>::construct(__outer_alloc, __p,
|
||||||
|
allocator_arg, __inner_alloc,
|
||||||
|
std::forward<_Args>(__args)...);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename _OuterAlloc,
|
||||||
|
typename _InnerAlloc, typename _Tp, typename... _Args>
|
||||||
|
inline void __dispatch_scoped_construct(std::true_type __uses_alloc,
|
||||||
|
std::false_type __use_alloc_prefix,
|
||||||
|
_OuterAlloc& __outer_alloc,
|
||||||
|
_InnerAlloc& __inner_alloc,
|
||||||
|
_Tp* __p, _Args&&... __args)
|
||||||
|
{
|
||||||
|
// If _Tp uses an allocator compatible with _InnerAlloc,
|
||||||
|
// but the specific constructor does not have a variant that
|
||||||
|
// takes an allocator argument, then program is malformed.
|
||||||
|
// static_assert(has_constructor<_Tp, _Args...>::value,
|
||||||
|
// "Cannot pass inner allocator to this constructor");
|
||||||
|
|
||||||
|
allocator_traits<_OuterAlloc>::construct(
|
||||||
|
__outer_alloc, __p, std::forward<_Args>(__args)...,
|
||||||
|
__inner_alloc);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename _OuterAlloc, typename _InnerAlloc,
|
||||||
|
typename _Tp, typename... _Args>
|
||||||
|
inline void __do_scoped_construct(std::false_type __scoped_outer,
|
||||||
|
_OuterAlloc& __outer_alloc,
|
||||||
|
_InnerAlloc& __inner_alloc,
|
||||||
|
_Tp* __p, _Args&&... __args)
|
||||||
|
{
|
||||||
|
// Dispatch construction to the correct __dispatch_scoped_construct()
|
||||||
|
// function based on whether _Tp uses an allocator of type
|
||||||
|
// _InnerAlloc and, if so, whether there exists the following
|
||||||
|
// constructor:
|
||||||
|
// _Tp(allocator_arg_t, _InnerAlloc, Args...).
|
||||||
|
auto __uses_alloc = uses_allocator<_Tp, _InnerAlloc>();
|
||||||
|
auto __use_alloc_prefix = __has_ctor<_Tp>(0, allocator_arg,
|
||||||
|
__inner_alloc,
|
||||||
|
std::forward<_Args>(__args)...);
|
||||||
|
__dispatch_scoped_construct(__uses_alloc, __use_alloc_prefix,
|
||||||
|
__outer_alloc,
|
||||||
|
__inner_alloc,
|
||||||
|
__p, std::forward<_Args>(__args)...);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename _OuterAlloc, typename _InnerAlloc,
|
||||||
|
typename _Tp, typename... _Args>
|
||||||
|
void __do_scoped_construct(std::true_type __scoped_outer,
|
||||||
|
_OuterAlloc& __outer_alloc,
|
||||||
|
_InnerAlloc& __inner_alloc,
|
||||||
|
_Tp* __p, _Args&&... __args)
|
||||||
|
{
|
||||||
|
// Use outermost allocator if __outer_alloc is scoped
|
||||||
|
typedef typename _OuterAlloc::outer_allocator_type outerouter;
|
||||||
|
__do_scoped_construct(__is_scoped_allocator<outerouter>(),
|
||||||
|
__outer_alloc.outer_allocator(),
|
||||||
|
__inner_alloc,
|
||||||
|
__p, std::forward<_Args>(__args)...);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // end namespace __details
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Implementation of scoped_allocator_adaptor
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor(const scoped_allocator_adaptor& other)
|
||||||
|
: _Base(other)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor(const scoped_allocator_adaptor<OuterA2,
|
||||||
|
InnerAllocs...>& other)
|
||||||
|
: _Base(other)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor(scoped_allocator_adaptor<OuterA2, InnerAllocs...>&& other)
|
||||||
|
: _Base(std::move(other))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <typename OuterA2>
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
scoped_allocator_adaptor(OuterA2&& outerAlloc, const InnerAllocs&... innerAllocs)
|
||||||
|
: _Base(std::forward<OuterA2>(outerAlloc), innerAllocs...)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
~scoped_allocator_adaptor()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
inline typename allocator_traits<OuterAlloc>::pointer
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
allocate(size_type n)
|
||||||
|
{
|
||||||
|
return allocator_traits<OuterAlloc>::allocate(outer_allocator(), n);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
inline typename allocator_traits<OuterAlloc>::pointer
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
allocate(size_type n, const_void_pointer hint)
|
||||||
|
{
|
||||||
|
return allocator_traits<OuterAlloc>::allocate(outer_allocator(), n, hint);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
inline void scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
deallocate(pointer p, size_type n)
|
||||||
|
{
|
||||||
|
allocator_traits<OuterAlloc>::deallocate(outer_allocator(), p, n);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
inline typename allocator_traits<OuterAlloc>::size_type
|
||||||
|
scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::max_size() const
|
||||||
|
{
|
||||||
|
return allocator_traits<OuterAlloc>::max_size(outer_allocator());
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <typename T>
|
||||||
|
inline void scoped_allocator_adaptor<OuterAlloc, InnerAllocs...>::
|
||||||
|
destroy(T* p)
|
||||||
|
{
|
||||||
|
allocator_traits<OuterAlloc>::destroy(outer_allocator(), p);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <typename T, typename... Args>
|
||||||
|
inline
|
||||||
|
void scoped_allocator_adaptor<OuterAlloc,InnerAllocs...>::construct(T* p,
|
||||||
|
Args&&... args)
|
||||||
|
{
|
||||||
|
__do_scoped_construct(__details::__is_scoped_allocator<OuterAlloc>(),
|
||||||
|
this->outer_allocator(), this->inner_allocator(),
|
||||||
|
p, std::forward<Args>(args)...);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <class T1, class T2>
|
||||||
|
void scoped_allocator_adaptor<OuterAlloc,InnerAllocs...>::construct(
|
||||||
|
std::pair<T1,T2>* p)
|
||||||
|
{
|
||||||
|
construct(addressof(p->first));
|
||||||
|
try {
|
||||||
|
construct(addressof(p->second));
|
||||||
|
}
|
||||||
|
catch (...) {
|
||||||
|
destroy(addressof(p->first));
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <class T1, class T2, class U, class V>
|
||||||
|
void scoped_allocator_adaptor<OuterAlloc,InnerAllocs...>::construct(
|
||||||
|
std::pair<T1,T2>* p, U&& x, V&& y)
|
||||||
|
{
|
||||||
|
construct(addressof(p->first), std::forward<U>(x));
|
||||||
|
try {
|
||||||
|
construct(addressof(p->second), std::forward<V>(y));
|
||||||
|
}
|
||||||
|
catch (...) {
|
||||||
|
destroy(addressof(p->first));
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <class T1, class T2, class U, class V>
|
||||||
|
void scoped_allocator_adaptor<OuterAlloc,InnerAllocs...>::construct(
|
||||||
|
std::pair<T1,T2>* p, const std::pair<U, V>& pr)
|
||||||
|
{
|
||||||
|
construct(addressof(p->first), pr.first);
|
||||||
|
try {
|
||||||
|
construct(addressof(p->second), pr.second);
|
||||||
|
}
|
||||||
|
catch (...) {
|
||||||
|
destroy(addressof(p->first));
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterAlloc, typename... InnerAllocs>
|
||||||
|
template <class T1, class T2, class U, class V>
|
||||||
|
void scoped_allocator_adaptor<OuterAlloc,InnerAllocs...>::construct(
|
||||||
|
std::pair<T1,T2>* p, std::pair<U, V>&& pr)
|
||||||
|
{
|
||||||
|
construct(addressof(p->first), std::move(pr.first));
|
||||||
|
try {
|
||||||
|
construct(addressof(p->second), std::move(pr.second));
|
||||||
|
}
|
||||||
|
catch (...) {
|
||||||
|
destroy(addressof(p->first));
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterA1, typename OuterA2, typename... InnerAllocs>
|
||||||
|
inline
|
||||||
|
bool operator==(const scoped_allocator_adaptor<OuterA1,InnerAllocs...>& a,
|
||||||
|
const scoped_allocator_adaptor<OuterA2,InnerAllocs...>& b)
|
||||||
|
{
|
||||||
|
return a.outer_allocator() == b.outer_allocator()
|
||||||
|
&& a.inner_allocator() == b.inner_allocator();
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterA1, typename OuterA2>
|
||||||
|
inline
|
||||||
|
bool operator==(const scoped_allocator_adaptor<OuterA1>& a,
|
||||||
|
const scoped_allocator_adaptor<OuterA2>& b)
|
||||||
|
{
|
||||||
|
return a.outer_allocator() == b.outer_allocator();
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename OuterA1, typename OuterA2, typename... InnerAllocs>
|
||||||
|
inline
|
||||||
|
bool operator!=(const scoped_allocator_adaptor<OuterA1,InnerAllocs...>& a,
|
||||||
|
const scoped_allocator_adaptor<OuterA2,InnerAllocs...>& b)
|
||||||
|
{
|
||||||
|
return ! (a == b);
|
||||||
|
}
|
||||||
|
|
||||||
|
}} // namespace boost { namespace container {
|
||||||
|
|
||||||
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
|
#endif // BOOST_CONTAINER_ALLOCATOR_SCOPED_ALLOCATOR_HPP
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_CONTAINERS_FWD_HPP
|
#ifndef BOOST_CONTAINER_CONTAINER_FWD_HPP
|
||||||
#define BOOST_CONTAINERS_CONTAINERS_FWD_HPP
|
#define BOOST_CONTAINER_CONTAINER_FWD_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -26,38 +26,17 @@ namespace intrusive{
|
|||||||
//Create namespace to avoid compilation errors
|
//Create namespace to avoid compilation errors
|
||||||
}}
|
}}
|
||||||
|
|
||||||
namespace boost{ namespace container{ namespace containers_detail{
|
namespace boost{ namespace container{ namespace container_detail{
|
||||||
|
|
||||||
namespace bi = boost::intrusive;
|
namespace bi = boost::intrusive;
|
||||||
|
|
||||||
}}}
|
}}}
|
||||||
|
|
||||||
#ifndef _LIBCPP_VERSION
|
|
||||||
|
|
||||||
namespace std {
|
|
||||||
|
|
||||||
template <class T>
|
|
||||||
class allocator;
|
|
||||||
|
|
||||||
template <class T>
|
|
||||||
struct less;
|
|
||||||
|
|
||||||
template <class T1, class T2>
|
|
||||||
struct pair;
|
|
||||||
|
|
||||||
template <class CharType>
|
|
||||||
struct char_traits;
|
|
||||||
|
|
||||||
} //namespace std {
|
|
||||||
|
|
||||||
#else
|
|
||||||
|
|
||||||
#include <utility>
|
#include <utility>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
#include <functional>
|
#include <functional>
|
||||||
#include <iosfwd>
|
#include <iosfwd>
|
||||||
|
#include <string>
|
||||||
#endif
|
|
||||||
|
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
@@ -195,4 +174,4 @@ struct dummy
|
|||||||
|
|
||||||
}} //namespace boost { namespace container {
|
}} //namespace boost { namespace container {
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_CONTAINERS_FWD_HPP
|
#endif //#ifndef BOOST_CONTAINER_CONTAINER_FWD_HPP
|
||||||
|
File diff suppressed because it is too large
Load Diff
@@ -19,7 +19,7 @@
|
|||||||
#include <boost/container/container_fwd.hpp>
|
#include <boost/container/container_fwd.hpp>
|
||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
#include <boost/container/detail/utilities.hpp>
|
#include <boost/container/detail/utilities.hpp>
|
||||||
#include <boost/pointer_to_other.hpp>
|
#include <boost/intrusive/pointer_traits.hpp>
|
||||||
#include <boost/intrusive/set.hpp>
|
#include <boost/intrusive/set.hpp>
|
||||||
#include <boost/intrusive/slist.hpp>
|
#include <boost/intrusive/slist.hpp>
|
||||||
#include <boost/container/detail/type_traits.hpp>
|
#include <boost/container/detail/type_traits.hpp>
|
||||||
@@ -31,7 +31,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class size_type>
|
template<class size_type>
|
||||||
struct hdr_offset_holder_t
|
struct hdr_offset_holder_t
|
||||||
@@ -221,7 +221,7 @@ class private_adaptive_node_pool_impl
|
|||||||
|
|
||||||
//!Returns the segment manager. Never throws
|
//!Returns the segment manager. Never throws
|
||||||
segment_manager_base_type* get_segment_manager_base()const
|
segment_manager_base_type* get_segment_manager_base()const
|
||||||
{ return containers_detail::get_pointer(mp_segment_mngr_base); }
|
{ return container_detail::to_raw_pointer(mp_segment_mngr_base); }
|
||||||
|
|
||||||
//!Allocates array of count elements. Can throw
|
//!Allocates array of count elements. Can throw
|
||||||
void *allocate_node()
|
void *allocate_node()
|
||||||
@@ -348,7 +348,7 @@ class private_adaptive_node_pool_impl
|
|||||||
{
|
{
|
||||||
block_iterator block_it(m_block_multiset.end());
|
block_iterator block_it(m_block_multiset.end());
|
||||||
while(n--){
|
while(n--){
|
||||||
void *pElem = containers_detail::get_pointer(chain.front());
|
void *pElem = container_detail::to_raw_pointer(chain.front());
|
||||||
chain.pop_front();
|
chain.pop_front();
|
||||||
priv_invariants();
|
priv_invariants();
|
||||||
block_info_t *block_info = this->priv_block_from_node(pElem);
|
block_info_t *block_info = this->priv_block_from_node(pElem);
|
||||||
@@ -434,7 +434,7 @@ class private_adaptive_node_pool_impl
|
|||||||
(void)free_nodes;
|
(void)free_nodes;
|
||||||
BOOST_ASSERT(free_nodes == mp_impl->m_real_num_node);
|
BOOST_ASSERT(free_nodes == mp_impl->m_real_num_node);
|
||||||
BOOST_ASSERT(0 == to_deallocate->hdr_offset);
|
BOOST_ASSERT(0 == to_deallocate->hdr_offset);
|
||||||
hdr_offset_holder *hdr_off_holder = mp_impl->priv_first_subblock_from_block(containers_detail::get_pointer(to_deallocate));
|
hdr_offset_holder *hdr_off_holder = mp_impl->priv_first_subblock_from_block(container_detail::to_raw_pointer(to_deallocate));
|
||||||
mp_impl->mp_segment_mngr_base->deallocate(hdr_off_holder);
|
mp_impl->mp_segment_mngr_base->deallocate(hdr_off_holder);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -557,7 +557,7 @@ class private_adaptive_node_pool_impl
|
|||||||
(mp_segment_mngr_base->allocate_aligned(real_block_size, m_real_block_alignment));
|
(mp_segment_mngr_base->allocate_aligned(real_block_size, m_real_block_alignment));
|
||||||
if(!mem_address) throw std::bad_alloc();
|
if(!mem_address) throw std::bad_alloc();
|
||||||
++m_totally_free_blocks;
|
++m_totally_free_blocks;
|
||||||
block_info_t *c_info = new(mem_address)block_info_t;
|
block_info_t *c_info = new(mem_address)block_info_t();
|
||||||
m_block_multiset.insert(m_block_multiset.end(), *c_info);
|
m_block_multiset.insert(m_block_multiset.end(), *c_info);
|
||||||
|
|
||||||
mem_address += HdrSize;
|
mem_address += HdrSize;
|
||||||
@@ -587,7 +587,7 @@ class private_adaptive_node_pool_impl
|
|||||||
|
|
||||||
//First initialize header information on the last subblock
|
//First initialize header information on the last subblock
|
||||||
char *hdr_addr = mem_address + m_real_block_alignment*(m_num_subblocks-1);
|
char *hdr_addr = mem_address + m_real_block_alignment*(m_num_subblocks-1);
|
||||||
block_info_t *c_info = new(hdr_addr)block_info_t;
|
block_info_t *c_info = new(hdr_addr)block_info_t();
|
||||||
//Some structural checks
|
//Some structural checks
|
||||||
BOOST_ASSERT(static_cast<void*>(&static_cast<hdr_offset_holder*>(c_info)->hdr_offset) ==
|
BOOST_ASSERT(static_cast<void*>(&static_cast<hdr_offset_holder*>(c_info)->hdr_offset) ==
|
||||||
static_cast<void*>(c_info));
|
static_cast<void*>(c_info));
|
||||||
@@ -622,8 +622,8 @@ class private_adaptive_node_pool_impl
|
|||||||
{ return priv_alloc_block(n, IsAlignOnly()); }
|
{ return priv_alloc_block(n, IsAlignOnly()); }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef typename boost::pointer_to_other
|
typedef typename boost::intrusive::pointer_traits
|
||||||
<void_pointer, segment_manager_base_type>::type segment_mngr_base_ptr_t;
|
<void_pointer>::template rebind_pointer<segment_manager_base_type>::type segment_mngr_base_ptr_t;
|
||||||
const size_type m_max_free_blocks;
|
const size_type m_max_free_blocks;
|
||||||
const size_type m_real_node_size;
|
const size_type m_real_node_size;
|
||||||
//Round the size to a power of two value.
|
//Round the size to a power of two value.
|
||||||
@@ -639,7 +639,7 @@ class private_adaptive_node_pool_impl
|
|||||||
size_type m_totally_free_blocks; //Free blocks
|
size_type m_totally_free_blocks; //Free blocks
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_ADVANCED_INSERT_INT_HPP
|
#ifndef BOOST_CONTAINER_ADVANCED_INSERT_INT_HPP
|
||||||
#define BOOST_CONTAINERS_ADVANCED_INSERT_INT_HPP
|
#define BOOST_CONTAINER_ADVANCED_INSERT_INT_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -17,54 +17,58 @@
|
|||||||
|
|
||||||
#include "config_begin.hpp"
|
#include "config_begin.hpp"
|
||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
#include <iterator> //std::iterator_traits
|
#include <iterator> //std::iterator_traits
|
||||||
#include <new> //placement new
|
|
||||||
#include <boost/assert.hpp>
|
#include <boost/assert.hpp>
|
||||||
|
|
||||||
namespace boost { namespace container { namespace containers_detail {
|
namespace boost { namespace container { namespace container_detail {
|
||||||
|
|
||||||
//This class will be interface for operations dependent on FwdIt types used advanced_insert_aux_impl
|
//This class will be interface for operations dependent on FwdIt types used advanced_insert_aux_impl
|
||||||
template<class T, class Iterator>
|
template<class Iterator>
|
||||||
struct advanced_insert_aux_int
|
struct advanced_insert_aux_int
|
||||||
{
|
{
|
||||||
typedef typename std::iterator_traits<Iterator>::difference_type difference_type;
|
typedef typename std::iterator_traits<Iterator>::difference_type difference_type;
|
||||||
virtual void copy_all_to(Iterator p) = 0;
|
virtual void copy_remaining_to(Iterator p) = 0;
|
||||||
virtual void uninitialized_copy_all_to(Iterator p) = 0;
|
virtual void uninitialized_copy_remaining_to(Iterator p) = 0;
|
||||||
virtual void uninitialized_copy_some_and_update(Iterator pos, difference_type division_count, bool first) = 0;
|
virtual void uninitialized_copy_some_and_update(Iterator pos, difference_type division_count, bool first) = 0;
|
||||||
virtual void copy_some_and_update(Iterator pos, difference_type division_count, bool first) = 0;
|
virtual void copy_some_and_update(Iterator pos, difference_type division_count, bool first) = 0;
|
||||||
virtual ~advanced_insert_aux_int() {}
|
virtual ~advanced_insert_aux_int() {}
|
||||||
};
|
};
|
||||||
|
|
||||||
//This class template will adapt each FwIt types to advanced_insert_aux_int
|
//This class template will adapt each FwIt types to advanced_insert_aux_int
|
||||||
template<class T, class FwdIt, class Iterator>
|
template<class A, class FwdIt, class Iterator>
|
||||||
struct advanced_insert_aux_proxy
|
struct advanced_insert_aux_proxy
|
||||||
: public advanced_insert_aux_int<T, Iterator>
|
: public advanced_insert_aux_int<Iterator>
|
||||||
{
|
{
|
||||||
typedef typename advanced_insert_aux_int<T, Iterator>::difference_type difference_type;
|
typedef boost::container::allocator_traits<A> alloc_traits;
|
||||||
advanced_insert_aux_proxy(FwdIt first, FwdIt last)
|
typedef typename allocator_traits<A>::size_type size_type;
|
||||||
: first_(first), last_(last)
|
typedef typename allocator_traits<A>::value_type value_type;
|
||||||
|
typedef typename advanced_insert_aux_int<Iterator>::difference_type difference_type;
|
||||||
|
|
||||||
|
advanced_insert_aux_proxy(A& a, FwdIt first, FwdIt last)
|
||||||
|
: a_(a), first_(first), last_(last)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
virtual ~advanced_insert_aux_proxy()
|
virtual ~advanced_insert_aux_proxy()
|
||||||
{}
|
{}
|
||||||
|
|
||||||
virtual void copy_all_to(Iterator p)
|
virtual void copy_remaining_to(Iterator p)
|
||||||
{ ::boost::copy_or_move(first_, last_, p); }
|
{ ::boost::copy_or_move(first_, last_, p); }
|
||||||
|
|
||||||
virtual void uninitialized_copy_all_to(Iterator p)
|
virtual void uninitialized_copy_remaining_to(Iterator p)
|
||||||
{ ::boost::uninitialized_copy_or_move(first_, last_, p); }
|
{ ::boost::container::uninitialized_copy_or_move_alloc(a_, first_, last_, p); }
|
||||||
|
|
||||||
virtual void uninitialized_copy_some_and_update(Iterator pos, difference_type division_count, bool first_n)
|
virtual void uninitialized_copy_some_and_update(Iterator pos, difference_type division_count, bool first_n)
|
||||||
{
|
{
|
||||||
FwdIt mid = first_;
|
FwdIt mid = first_;
|
||||||
std::advance(mid, division_count);
|
std::advance(mid, division_count);
|
||||||
if(first_n){
|
if(first_n){
|
||||||
::boost::uninitialized_copy_or_move(first_, mid, pos);
|
::boost::container::uninitialized_copy_or_move_alloc(a_, first_, mid, pos);
|
||||||
first_ = mid;
|
first_ = mid;
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
::boost::uninitialized_copy_or_move(mid, last_, pos);
|
::boost::container::uninitialized_copy_or_move_alloc(a_, mid, last_, pos);
|
||||||
last_ = mid;
|
last_ = mid;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -82,53 +86,38 @@ struct advanced_insert_aux_proxy
|
|||||||
last_ = mid;
|
last_ = mid;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
A &a_;
|
||||||
FwdIt first_, last_;
|
FwdIt first_, last_;
|
||||||
};
|
};
|
||||||
|
|
||||||
//This class template will adapt each FwIt types to advanced_insert_aux_int
|
//This class template will adapt default construction insertions to advanced_insert_aux_int
|
||||||
template<class T, class Iterator, class SizeType>
|
template<class A, class Iterator>
|
||||||
struct default_construct_aux_proxy
|
struct default_construct_aux_proxy
|
||||||
: public advanced_insert_aux_int<T, Iterator>
|
: public advanced_insert_aux_int<Iterator>
|
||||||
{
|
{
|
||||||
typedef typename advanced_insert_aux_int<T, Iterator>::difference_type difference_type;
|
typedef boost::container::allocator_traits<A> alloc_traits;
|
||||||
default_construct_aux_proxy(SizeType count)
|
typedef typename allocator_traits<A>::size_type size_type;
|
||||||
: count_(count)
|
typedef typename allocator_traits<A>::value_type value_type;
|
||||||
{}
|
typedef typename advanced_insert_aux_int<Iterator>::difference_type difference_type;
|
||||||
|
|
||||||
void uninitialized_copy_impl(Iterator p, const SizeType n)
|
default_construct_aux_proxy(A &a, size_type count)
|
||||||
{
|
: a_(a), count_(count)
|
||||||
BOOST_ASSERT(n <= count_);
|
{}
|
||||||
Iterator orig_p = p;
|
|
||||||
SizeType i = 0;
|
|
||||||
try{
|
|
||||||
for(; i < n; ++i, ++p){
|
|
||||||
new(containers_detail::get_pointer(&*p))T();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch(...){
|
|
||||||
while(i--){
|
|
||||||
containers_detail::get_pointer(&*orig_p++)->~T();
|
|
||||||
}
|
|
||||||
throw;
|
|
||||||
}
|
|
||||||
count_ -= n;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual ~default_construct_aux_proxy()
|
virtual ~default_construct_aux_proxy()
|
||||||
{}
|
{}
|
||||||
|
|
||||||
virtual void copy_all_to(Iterator)
|
virtual void copy_remaining_to(Iterator)
|
||||||
{ //This should never be called with any count
|
{ //This should never be called with any count
|
||||||
BOOST_ASSERT(count_ == 0);
|
BOOST_ASSERT(count_ == 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void uninitialized_copy_all_to(Iterator p)
|
virtual void uninitialized_copy_remaining_to(Iterator p)
|
||||||
{ this->uninitialized_copy_impl(p, count_); }
|
{ this->priv_uninitialized_copy(p, count_); }
|
||||||
|
|
||||||
virtual void uninitialized_copy_some_and_update(Iterator pos, difference_type division_count, bool first_n)
|
virtual void uninitialized_copy_some_and_update(Iterator pos, difference_type division_count, bool first_n)
|
||||||
{
|
{
|
||||||
SizeType new_count;
|
size_type new_count;
|
||||||
if(first_n){
|
if(first_n){
|
||||||
new_count = division_count;
|
new_count = division_count;
|
||||||
}
|
}
|
||||||
@@ -136,13 +125,13 @@ struct default_construct_aux_proxy
|
|||||||
BOOST_ASSERT(difference_type(count_)>= division_count);
|
BOOST_ASSERT(difference_type(count_)>= division_count);
|
||||||
new_count = count_ - division_count;
|
new_count = count_ - division_count;
|
||||||
}
|
}
|
||||||
this->uninitialized_copy_impl(pos, new_count);
|
this->priv_uninitialized_copy(pos, new_count);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void copy_some_and_update(Iterator , difference_type division_count, bool first_n)
|
virtual void copy_some_and_update(Iterator , difference_type division_count, bool first_n)
|
||||||
{
|
{
|
||||||
BOOST_ASSERT(count_ == 0);
|
BOOST_ASSERT(count_ == 0);
|
||||||
SizeType new_count;
|
size_type new_count;
|
||||||
if(first_n){
|
if(first_n){
|
||||||
new_count = division_count;
|
new_count = division_count;
|
||||||
}
|
}
|
||||||
@@ -155,12 +144,32 @@ struct default_construct_aux_proxy
|
|||||||
(void)new_count;
|
(void)new_count;
|
||||||
}
|
}
|
||||||
|
|
||||||
SizeType count_;
|
private:
|
||||||
|
void priv_uninitialized_copy(Iterator p, const size_type n)
|
||||||
|
{
|
||||||
|
BOOST_ASSERT(n <= count_);
|
||||||
|
Iterator orig_p = p;
|
||||||
|
size_type i = 0;
|
||||||
|
try{
|
||||||
|
for(; i < n; ++i, ++p){
|
||||||
|
alloc_traits::construct(a_, container_detail::to_raw_pointer(&*p));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch(...){
|
||||||
|
while(i--){
|
||||||
|
alloc_traits::destroy(a_, container_detail::to_raw_pointer(&*orig_p++));
|
||||||
|
}
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
count_ -= n;
|
||||||
|
}
|
||||||
|
A &a_;
|
||||||
|
size_type count_;
|
||||||
};
|
};
|
||||||
|
|
||||||
}}} //namespace boost { namespace container { namespace containers_detail {
|
}}} //namespace boost { namespace container { namespace container_detail {
|
||||||
|
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
#include <boost/container/detail/variadic_templates_tools.hpp>
|
#include <boost/container/detail/variadic_templates_tools.hpp>
|
||||||
#include <boost/container/detail/stored_ref.hpp>
|
#include <boost/container/detail/stored_ref.hpp>
|
||||||
@@ -169,217 +178,251 @@ struct default_construct_aux_proxy
|
|||||||
//#include <iostream> //For debugging purposes
|
//#include <iostream> //For debugging purposes
|
||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
//This class template will adapt each FwIt types to advanced_insert_aux_int
|
|
||||||
template<class T, class Iterator, class ...Args>
|
//This class template will adapt emplace construction insertions of movable types
|
||||||
struct advanced_insert_aux_emplace
|
//to advanced_insert_aux_int
|
||||||
: public advanced_insert_aux_int<T, Iterator>
|
template<class A, class Iterator, class ...Args>
|
||||||
|
struct advanced_insert_aux_non_movable_emplace
|
||||||
|
: public advanced_insert_aux_int<Iterator>
|
||||||
{
|
{
|
||||||
typedef typename advanced_insert_aux_int<T, Iterator>::difference_type difference_type;
|
typedef boost::container::allocator_traits<A> alloc_traits;
|
||||||
|
typedef typename allocator_traits<A>::size_type size_type;
|
||||||
|
typedef typename allocator_traits<A>::value_type value_type;
|
||||||
|
typedef typename advanced_insert_aux_int<Iterator>::difference_type difference_type;
|
||||||
typedef typename build_number_seq<sizeof...(Args)>::type index_tuple_t;
|
typedef typename build_number_seq<sizeof...(Args)>::type index_tuple_t;
|
||||||
|
|
||||||
explicit advanced_insert_aux_emplace(Args&&... args)
|
explicit advanced_insert_aux_non_movable_emplace(A &a, Args&&... args)
|
||||||
: args_(args...)
|
: a_(a)
|
||||||
|
, args_(args...)
|
||||||
, used_(false)
|
, used_(false)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
~advanced_insert_aux_emplace()
|
~advanced_insert_aux_non_movable_emplace()
|
||||||
{}
|
{}
|
||||||
|
|
||||||
virtual void copy_all_to(Iterator p)
|
virtual void copy_remaining_to(Iterator)
|
||||||
{ this->priv_copy_all_to(index_tuple_t(), p); }
|
//This code can't be called since value_type is not movable or copyable
|
||||||
|
{ BOOST_ASSERT(false); }
|
||||||
|
|
||||||
virtual void uninitialized_copy_all_to(Iterator p)
|
virtual void uninitialized_copy_remaining_to(Iterator p)
|
||||||
{ this->priv_uninitialized_copy_all_to(index_tuple_t(), p); }
|
{ this->priv_uninitialized_copy_remaining_to(index_tuple_t(), p); }
|
||||||
|
|
||||||
virtual void uninitialized_copy_some_and_update(Iterator p, difference_type division_count, bool first_n)
|
virtual void uninitialized_copy_some_and_update(Iterator p, difference_type division_count, bool first_n)
|
||||||
{ this->priv_uninitialized_copy_some_and_update(index_tuple_t(), p, division_count, first_n); }
|
{ this->priv_uninitialized_copy_some_and_update(index_tuple_t(), p, division_count, first_n); }
|
||||||
|
|
||||||
virtual void copy_some_and_update(Iterator p, difference_type division_count, bool first_n)
|
virtual void copy_some_and_update(Iterator, difference_type, bool )
|
||||||
{ this->priv_copy_some_and_update(index_tuple_t(), p, division_count, first_n); }
|
//This code can't be called since value_type is not movable or copyable
|
||||||
|
{ BOOST_ASSERT(false); }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
template<int ...IdxPack>
|
|
||||||
void priv_copy_all_to(const index_tuple<IdxPack...>&, Iterator p)
|
|
||||||
{
|
|
||||||
if(!used_){
|
|
||||||
*p = boost::move(T (::boost::container::containers_detail::stored_ref<Args>::forward(get<IdxPack>(args_))...));
|
|
||||||
used_ = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
template<int ...IdxPack>
|
|
||||||
void priv_uninitialized_copy_all_to(const index_tuple<IdxPack...>&, Iterator p)
|
|
||||||
{
|
|
||||||
if(!used_){
|
|
||||||
new(containers_detail::get_pointer(&*p))T(::boost::container::containers_detail::stored_ref<Args>::forward(get<IdxPack>(args_))...);
|
|
||||||
used_ = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
template<int ...IdxPack>
|
template<int ...IdxPack>
|
||||||
void priv_uninitialized_copy_some_and_update(const index_tuple<IdxPack...>&, Iterator p, difference_type division_count, bool first_n)
|
void priv_uninitialized_copy_some_and_update(const index_tuple<IdxPack...>&, Iterator p, difference_type division_count, bool first_n)
|
||||||
{
|
{
|
||||||
BOOST_ASSERT(division_count <=1);
|
BOOST_ASSERT(division_count <=1);
|
||||||
if((first_n && division_count == 1) || (!first_n && division_count == 0)){
|
if((first_n && division_count == 1) || (!first_n && division_count == 0)){
|
||||||
if(!used_){
|
if(!used_){
|
||||||
new(containers_detail::get_pointer(&*p))T(::boost::container::containers_detail::stored_ref<Args>::forward(get<IdxPack>(args_))...);
|
alloc_traits::construct( a_
|
||||||
|
, container_detail::to_raw_pointer(&*p)
|
||||||
|
, ::boost::container::container_detail::
|
||||||
|
stored_ref<Args>::forward(get<IdxPack>(args_))...
|
||||||
|
);
|
||||||
used_ = true;
|
used_ = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<int ...IdxPack>
|
||||||
|
void priv_uninitialized_copy_remaining_to(const index_tuple<IdxPack...>&, Iterator p)
|
||||||
|
{
|
||||||
|
if(!used_){
|
||||||
|
alloc_traits::construct( a_
|
||||||
|
, container_detail::to_raw_pointer(&*p)
|
||||||
|
, ::boost::container::container_detail::
|
||||||
|
stored_ref<Args>::forward(get<IdxPack>(args_))...
|
||||||
|
);
|
||||||
|
used_ = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
A &a_;
|
||||||
|
tuple<Args&...> args_;
|
||||||
|
bool used_;
|
||||||
|
};
|
||||||
|
|
||||||
|
//This class template will adapt emplace construction insertions of movable types
|
||||||
|
//to advanced_insert_aux_int
|
||||||
|
template<class A, class Iterator, class ...Args>
|
||||||
|
struct advanced_insert_aux_emplace
|
||||||
|
: public advanced_insert_aux_non_movable_emplace<A, Iterator, Args...>
|
||||||
|
{
|
||||||
|
typedef advanced_insert_aux_non_movable_emplace<A, Iterator, Args...> base_t;
|
||||||
|
typedef typename base_t::value_type value_type;
|
||||||
|
typedef typename base_t::difference_type difference_type;
|
||||||
|
typedef typename base_t::index_tuple_t index_tuple_t;
|
||||||
|
|
||||||
|
explicit advanced_insert_aux_emplace(A &a, Args&&... args)
|
||||||
|
: base_t(a, boost::forward<Args>(args)...)
|
||||||
|
{}
|
||||||
|
|
||||||
|
~advanced_insert_aux_emplace()
|
||||||
|
{}
|
||||||
|
|
||||||
|
//Override only needed functions
|
||||||
|
virtual void copy_remaining_to(Iterator p)
|
||||||
|
{ this->priv_copy_remaining_to(index_tuple_t(), p); }
|
||||||
|
|
||||||
|
virtual void copy_some_and_update(Iterator p, difference_type division_count, bool first_n)
|
||||||
|
{ this->priv_copy_some_and_update(index_tuple_t(), p, division_count, first_n); }
|
||||||
|
|
||||||
|
private:
|
||||||
|
template<int ...IdxPack>
|
||||||
|
void priv_copy_remaining_to(const index_tuple<IdxPack...>&, Iterator p)
|
||||||
|
{
|
||||||
|
if(!this->used_){
|
||||||
|
*p = boost::move(value_type (
|
||||||
|
::boost::container::container_detail::stored_ref<Args>::forward(get<IdxPack>(this->args_))...));
|
||||||
|
this->used_ = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
template<int ...IdxPack>
|
template<int ...IdxPack>
|
||||||
void priv_copy_some_and_update(const index_tuple<IdxPack...>&, Iterator p, difference_type division_count, bool first_n)
|
void priv_copy_some_and_update(const index_tuple<IdxPack...>&, Iterator p, difference_type division_count, bool first_n)
|
||||||
{
|
{
|
||||||
BOOST_ASSERT(division_count <=1);
|
BOOST_ASSERT(division_count <=1);
|
||||||
if((first_n && division_count == 1) || (!first_n && division_count == 0)){
|
if((first_n && division_count == 1) || (!first_n && division_count == 0)){
|
||||||
if(!used_){
|
if(!this->used_){
|
||||||
*p = boost::move(T(::boost::container::containers_detail::stored_ref<Args>::forward(get<IdxPack>(args_))...));
|
*p = boost::move(value_type(
|
||||||
used_ = true;
|
::boost::container::container_detail::stored_ref<Args>::forward(get<IdxPack>(this->args_))...));
|
||||||
|
this->used_ = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
tuple<Args&...> args_;
|
|
||||||
bool used_;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
}}} //namespace boost { namespace container { namespace containers_detail {
|
}}} //namespace boost { namespace container { namespace container_detail {
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
#include <boost/container/detail/preprocessor.hpp>
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
#include <boost/container/detail/value_init.hpp>
|
#include <boost/container/detail/value_init.hpp>
|
||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
//This class template will adapt each FwIt types to advanced_insert_aux_int
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<class T, class Iterator>
|
template<class A, class Iterator BOOST_PP_ENUM_TRAILING_PARAMS(n, class P) > \
|
||||||
struct advanced_insert_aux_emplace
|
struct BOOST_PP_CAT(BOOST_PP_CAT(advanced_insert_aux_non_movable_emplace, n), arg) \
|
||||||
: public advanced_insert_aux_int<T, Iterator>
|
: public advanced_insert_aux_int<Iterator> \
|
||||||
{
|
{ \
|
||||||
typedef typename advanced_insert_aux_int<T, Iterator>::difference_type difference_type;
|
typedef boost::container::allocator_traits<A> alloc_traits; \
|
||||||
advanced_insert_aux_emplace()
|
typedef typename allocator_traits<A>::size_type size_type; \
|
||||||
: used_(false)
|
typedef typename allocator_traits<A>::value_type value_type; \
|
||||||
{}
|
typedef typename advanced_insert_aux_int<Iterator>::difference_type \
|
||||||
|
difference_type; \
|
||||||
~advanced_insert_aux_emplace()
|
\
|
||||||
{}
|
BOOST_PP_CAT(BOOST_PP_CAT(advanced_insert_aux_non_movable_emplace, n), arg) \
|
||||||
|
( A &a BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _) ) \
|
||||||
virtual void copy_all_to(Iterator p)
|
: a_(a) \
|
||||||
{
|
, used_(false) \
|
||||||
if(!used_){
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_INIT, _) \
|
||||||
value_init<T>v;
|
{} \
|
||||||
*p = boost::move(v.m_t);
|
\
|
||||||
used_ = true;
|
virtual void copy_remaining_to(Iterator) \
|
||||||
}
|
{ BOOST_ASSERT(false); } \
|
||||||
}
|
\
|
||||||
|
virtual void uninitialized_copy_remaining_to(Iterator p) \
|
||||||
virtual void uninitialized_copy_all_to(Iterator p)
|
{ \
|
||||||
{
|
if(!used_){ \
|
||||||
if(!used_){
|
alloc_traits::construct \
|
||||||
new(containers_detail::get_pointer(&*p))T();
|
( a_ \
|
||||||
used_ = true;
|
, container_detail::to_raw_pointer(&*p) \
|
||||||
}
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_MEMBER_FORWARD, _) \
|
||||||
}
|
); \
|
||||||
|
used_ = true; \
|
||||||
virtual void uninitialized_copy_some_and_update(Iterator p, difference_type division_count, bool first_n)
|
} \
|
||||||
{
|
} \
|
||||||
BOOST_ASSERT(division_count <=1);
|
\
|
||||||
if((first_n && division_count == 1) || (!first_n && division_count == 0)){
|
virtual void uninitialized_copy_some_and_update \
|
||||||
if(!used_){
|
(Iterator p, difference_type division_count, bool first_n) \
|
||||||
new(containers_detail::get_pointer(&*p))T();
|
{ \
|
||||||
used_ = true;
|
BOOST_ASSERT(division_count <=1); \
|
||||||
}
|
if((first_n && division_count == 1) || (!first_n && division_count == 0)){ \
|
||||||
}
|
if(!used_){ \
|
||||||
}
|
alloc_traits::construct \
|
||||||
|
( a_ \
|
||||||
virtual void copy_some_and_update(Iterator p, difference_type division_count, bool first_n)
|
, container_detail::to_raw_pointer(&*p) \
|
||||||
{
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_MEMBER_FORWARD, _) \
|
||||||
BOOST_ASSERT(division_count <=1);
|
); \
|
||||||
if((first_n && division_count == 1) || (!first_n && division_count == 0)){
|
used_ = true; \
|
||||||
if(!used_){
|
} \
|
||||||
value_init<T>v;
|
} \
|
||||||
*p = boost::move(v.m_t);
|
} \
|
||||||
used_ = true;
|
\
|
||||||
}
|
virtual void copy_some_and_update(Iterator, difference_type, bool) \
|
||||||
}
|
{ BOOST_ASSERT(false); } \
|
||||||
}
|
\
|
||||||
private:
|
A &a_; \
|
||||||
bool used_;
|
bool used_; \
|
||||||
};
|
BOOST_PP_REPEAT(n, BOOST_CONTAINER_PP_PARAM_DEFINE, _) \
|
||||||
|
}; \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
\
|
||||||
template<class T, class Iterator, BOOST_PP_ENUM_PARAMS(n, class P) > \
|
template<class A, class Iterator BOOST_PP_ENUM_TRAILING_PARAMS(n, class P) > \
|
||||||
struct BOOST_PP_CAT(BOOST_PP_CAT(advanced_insert_aux_emplace, n), arg) \
|
struct BOOST_PP_CAT(BOOST_PP_CAT(advanced_insert_aux_emplace, n), arg) \
|
||||||
: public advanced_insert_aux_int<T, Iterator> \
|
: BOOST_PP_CAT(BOOST_PP_CAT( \
|
||||||
{ \
|
advanced_insert_aux_non_movable_emplace, n), arg) \
|
||||||
typedef typename advanced_insert_aux_int<T, Iterator>::difference_type difference_type; \
|
< A, Iterator BOOST_PP_ENUM_TRAILING_PARAMS(n, P) > \
|
||||||
\
|
{ \
|
||||||
BOOST_PP_CAT(BOOST_PP_CAT(advanced_insert_aux_emplace, n), arg) \
|
typedef BOOST_PP_CAT(BOOST_PP_CAT( \
|
||||||
( BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _) ) \
|
advanced_insert_aux_non_movable_emplace, n), arg) \
|
||||||
: used_(false), BOOST_PP_ENUM(n, BOOST_CONTAINERS_AUX_PARAM_INIT, _) {} \
|
<A, Iterator BOOST_PP_ENUM_TRAILING_PARAMS(n, P) > base_t; \
|
||||||
\
|
typedef typename base_t::value_type value_type; \
|
||||||
virtual void copy_all_to(Iterator p) \
|
typedef typename base_t::difference_type difference_type; \
|
||||||
{ \
|
\
|
||||||
if(!used_){ \
|
BOOST_PP_CAT(BOOST_PP_CAT(advanced_insert_aux_emplace, n), arg) \
|
||||||
T v(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_MEMBER_FORWARD, _)); \
|
( A &a BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _) ) \
|
||||||
*p = boost::move(v); \
|
: base_t(a BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) ) \
|
||||||
used_ = true; \
|
{} \
|
||||||
} \
|
\
|
||||||
} \
|
virtual void copy_remaining_to(Iterator p) \
|
||||||
\
|
{ \
|
||||||
virtual void uninitialized_copy_all_to(Iterator p) \
|
if(!this->used_){ \
|
||||||
{ \
|
value_type v BOOST_PP_LPAREN_IF(n) \
|
||||||
if(!used_){ \
|
BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_MEMBER_FORWARD, _) \
|
||||||
new(containers_detail::get_pointer(&*p))T \
|
BOOST_PP_RPAREN_IF(n); \
|
||||||
(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_MEMBER_FORWARD, _)); \
|
*p = boost::move(v); \
|
||||||
used_ = true; \
|
this->used_ = true; \
|
||||||
} \
|
} \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
virtual void uninitialized_copy_some_and_update \
|
virtual void copy_some_and_update \
|
||||||
(Iterator p, difference_type division_count, bool first_n) \
|
(Iterator p, difference_type division_count, bool first_n) \
|
||||||
{ \
|
{ \
|
||||||
BOOST_ASSERT(division_count <=1); \
|
BOOST_ASSERT(division_count <=1); \
|
||||||
if((first_n && division_count == 1) || (!first_n && division_count == 0)){ \
|
if((first_n && division_count == 1) || (!first_n && division_count == 0)){ \
|
||||||
if(!used_){ \
|
if(!this->used_){ \
|
||||||
new(containers_detail::get_pointer(&*p))T \
|
value_type v BOOST_PP_LPAREN_IF(n) \
|
||||||
(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_MEMBER_FORWARD, _)); \
|
BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_MEMBER_FORWARD, _) \
|
||||||
used_ = true; \
|
BOOST_PP_RPAREN_IF(n); \
|
||||||
} \
|
*p = boost::move(v); \
|
||||||
} \
|
this->used_ = true; \
|
||||||
} \
|
} \
|
||||||
\
|
} \
|
||||||
virtual void copy_some_and_update \
|
} \
|
||||||
(Iterator p, difference_type division_count, bool first_n) \
|
}; \
|
||||||
{ \
|
|
||||||
BOOST_ASSERT(division_count <=1); \
|
|
||||||
if((first_n && division_count == 1) || (!first_n && division_count == 0)){ \
|
|
||||||
if(!used_){ \
|
|
||||||
T v(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_MEMBER_FORWARD, _)); \
|
|
||||||
*p = boost::move(v); \
|
|
||||||
used_ = true; \
|
|
||||||
} \
|
|
||||||
} \
|
|
||||||
} \
|
|
||||||
\
|
|
||||||
bool used_; \
|
|
||||||
BOOST_PP_REPEAT(n, BOOST_CONTAINERS_AUX_PARAM_DEFINE, _) \
|
|
||||||
}; \
|
|
||||||
//!
|
//!
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
}}} //namespace boost { namespace container { namespace containers_detail {
|
}}} //namespace boost { namespace container { namespace container_detail {
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_ADVANCED_INSERT_INT_HPP
|
#endif //#ifndef BOOST_CONTAINER_ADVANCED_INSERT_INT_HPP
|
||||||
|
@@ -10,8 +10,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_ALGORITHMS_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_ALGORITHMS_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_ALGORITHMS_HPP
|
#define BOOST_CONTAINER_DETAIL_ALGORITHMS_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -23,7 +23,6 @@
|
|||||||
#include <boost/type_traits/has_trivial_copy.hpp>
|
#include <boost/type_traits/has_trivial_copy.hpp>
|
||||||
#include <boost/type_traits/has_trivial_assign.hpp>
|
#include <boost/type_traits/has_trivial_assign.hpp>
|
||||||
#include <boost/detail/no_exceptions_support.hpp>
|
#include <boost/detail/no_exceptions_support.hpp>
|
||||||
#include <boost/get_pointer.hpp>
|
|
||||||
|
|
||||||
#include <boost/container/detail/type_traits.hpp>
|
#include <boost/container/detail/type_traits.hpp>
|
||||||
#include <boost/container/detail/mpl.hpp>
|
#include <boost/container/detail/mpl.hpp>
|
||||||
@@ -33,56 +32,25 @@
|
|||||||
#include <cstring>
|
#include <cstring>
|
||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
|
|
||||||
#if defined(BOOST_NO_RVALUE_REFERENCES)
|
template<class A, class T, class InpIt>
|
||||||
template<class T>
|
inline void construct_in_place(A &a, T* dest, InpIt source)
|
||||||
struct has_own_construct_from_it
|
{ boost::container::allocator_traits<A>::construct(a, dest, *source); }
|
||||||
|
//#endif
|
||||||
|
|
||||||
|
template<class A, class T, class U, class D>
|
||||||
|
inline void construct_in_place(A &a, T *dest, default_construct_iterator<U, D>)
|
||||||
{
|
{
|
||||||
static const bool value = false;
|
boost::container::allocator_traits<A>::construct(a, dest);
|
||||||
};
|
|
||||||
|
|
||||||
namespace containers_detail {
|
|
||||||
|
|
||||||
template<class T, class InpIt>
|
|
||||||
inline void construct_in_place_impl(T* dest, const InpIt &source, containers_detail::true_)
|
|
||||||
{
|
|
||||||
T::construct(dest, *source);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
template<class T, class InpIt>
|
template<class A, class T, class U, class EF, class D>
|
||||||
inline void construct_in_place_impl(T* dest, const InpIt &source, containers_detail::false_)
|
inline void construct_in_place(A &a, T *dest, emplace_iterator<U, EF, D> ei)
|
||||||
{
|
{
|
||||||
new((void*)dest)T(*source);
|
ei.construct_in_place(a, dest);
|
||||||
}
|
}
|
||||||
|
/*
|
||||||
} //namespace containers_detail {
|
|
||||||
|
|
||||||
template<class T, class InpIt>
|
|
||||||
inline void construct_in_place(T* dest, InpIt source)
|
|
||||||
{
|
|
||||||
typedef containers_detail::bool_<has_own_construct_from_it<T>::value> boolean_t;
|
|
||||||
containers_detail::construct_in_place_impl(dest, source, boolean_t());
|
|
||||||
}
|
|
||||||
|
|
||||||
#else
|
|
||||||
template<class T, class InpIt>
|
|
||||||
inline void construct_in_place(T* dest, InpIt source)
|
|
||||||
{ ::new((void*)dest)T(*source); }
|
|
||||||
#endif
|
|
||||||
|
|
||||||
template<class T, class U, class D>
|
|
||||||
inline void construct_in_place(T *dest, default_construct_iterator<U, D>)
|
|
||||||
{
|
|
||||||
::new((void*)dest)T();
|
|
||||||
}
|
|
||||||
|
|
||||||
template<class T, class U, class E, class D>
|
|
||||||
inline void construct_in_place(T *dest, emplace_iterator<U, E, D> ei)
|
|
||||||
{
|
|
||||||
ei.construct_in_place(dest);
|
|
||||||
}
|
|
||||||
|
|
||||||
template<class InIt, class OutIt>
|
template<class InIt, class OutIt>
|
||||||
struct optimize_assign
|
struct optimize_assign
|
||||||
{
|
{
|
||||||
@@ -118,7 +86,7 @@ struct optimize_copy<T*, T*>
|
|||||||
{};
|
{};
|
||||||
|
|
||||||
template<class InIt, class OutIt> inline
|
template<class InIt, class OutIt> inline
|
||||||
OutIt copy_n_dispatch(InIt first, typename std::iterator_traits<InIt>::difference_type length, OutIt dest, containers_detail::bool_<false>)
|
OutIt copy_n_dispatch(InIt first, typename std::iterator_traits<InIt>::difference_type length, OutIt dest, container_detail::bool_<false>)
|
||||||
{
|
{
|
||||||
for (; length--; ++dest, ++first)
|
for (; length--; ++dest, ++first)
|
||||||
*dest = *first;
|
*dest = *first;
|
||||||
@@ -126,7 +94,7 @@ OutIt copy_n_dispatch(InIt first, typename std::iterator_traits<InIt>::differenc
|
|||||||
}
|
}
|
||||||
|
|
||||||
template<class T> inline
|
template<class T> inline
|
||||||
T *copy_n_dispatch(const T *first, typename std::iterator_traits<const T*>::difference_type length, T *dest, containers_detail::bool_<true>)
|
T *copy_n_dispatch(const T *first, typename std::iterator_traits<const T*>::difference_type length, T *dest, container_detail::bool_<true>)
|
||||||
{
|
{
|
||||||
std::size_t size = length*sizeof(T);
|
std::size_t size = length*sizeof(T);
|
||||||
return (static_cast<T*>(std::memmove(dest, first, size))) + size;
|
return (static_cast<T*>(std::memmove(dest, first, size))) + size;
|
||||||
@@ -136,14 +104,14 @@ template<class InIt, class OutIt> inline
|
|||||||
OutIt copy_n(InIt first, typename std::iterator_traits<InIt>::difference_type length, OutIt dest)
|
OutIt copy_n(InIt first, typename std::iterator_traits<InIt>::difference_type length, OutIt dest)
|
||||||
{
|
{
|
||||||
const bool do_optimized_assign = optimize_assign<InIt, OutIt>::value;
|
const bool do_optimized_assign = optimize_assign<InIt, OutIt>::value;
|
||||||
return copy_n_dispatch(first, length, dest, containers_detail::bool_<do_optimized_assign>());
|
return copy_n_dispatch(first, length, dest, container_detail::bool_<do_optimized_assign>());
|
||||||
}
|
}
|
||||||
|
|
||||||
template<class InIt, class FwdIt> inline
|
template<class InIt, class FwdIt> inline
|
||||||
FwdIt uninitialized_copy_n_dispatch
|
FwdIt uninitialized_copy_n_dispatch
|
||||||
(InIt first,
|
(InIt first,
|
||||||
typename std::iterator_traits<InIt>::difference_type count,
|
typename std::iterator_traits<InIt>::difference_type count,
|
||||||
FwdIt dest, containers_detail::bool_<false>)
|
FwdIt dest, container_detail::bool_<false>)
|
||||||
{
|
{
|
||||||
typedef typename std::iterator_traits<FwdIt>::value_type value_type;
|
typedef typename std::iterator_traits<FwdIt>::value_type value_type;
|
||||||
//Save initial destination position
|
//Save initial destination position
|
||||||
@@ -153,14 +121,14 @@ FwdIt uninitialized_copy_n_dispatch
|
|||||||
BOOST_TRY{
|
BOOST_TRY{
|
||||||
//Try to build objects
|
//Try to build objects
|
||||||
for (; --new_count; ++dest, ++first){
|
for (; --new_count; ++dest, ++first){
|
||||||
construct_in_place(containers_detail::get_pointer(&*dest), first);
|
construct_in_place(container_detail::to_raw_pointer(&*dest), first);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
BOOST_CATCH(...){
|
BOOST_CATCH(...){
|
||||||
//Call destructors
|
//Call destructors
|
||||||
new_count = count - new_count;
|
new_count = count - new_count;
|
||||||
for (; new_count--; ++dest_init){
|
for (; new_count--; ++dest_init){
|
||||||
containers_detail::get_pointer(&*dest_init)->~value_type();
|
container_detail::to_raw_pointer(&*dest_init)->~value_type();
|
||||||
}
|
}
|
||||||
BOOST_RETHROW
|
BOOST_RETHROW
|
||||||
}
|
}
|
||||||
@@ -168,7 +136,7 @@ FwdIt uninitialized_copy_n_dispatch
|
|||||||
return dest;
|
return dest;
|
||||||
}
|
}
|
||||||
template<class T> inline
|
template<class T> inline
|
||||||
T *uninitialized_copy_n_dispatch(const T *first, typename std::iterator_traits<const T*>::difference_type length, T *dest, containers_detail::bool_<true>)
|
T *uninitialized_copy_n_dispatch(const T *first, typename std::iterator_traits<const T*>::difference_type length, T *dest, container_detail::bool_<true>)
|
||||||
{
|
{
|
||||||
std::size_t size = length*sizeof(T);
|
std::size_t size = length*sizeof(T);
|
||||||
return (static_cast<T*>(std::memmove(dest, first, size))) + size;
|
return (static_cast<T*>(std::memmove(dest, first, size))) + size;
|
||||||
@@ -181,7 +149,7 @@ FwdIt uninitialized_copy_n
|
|||||||
FwdIt dest)
|
FwdIt dest)
|
||||||
{
|
{
|
||||||
const bool do_optimized_copy = optimize_copy<InIt, FwdIt>::value;
|
const bool do_optimized_copy = optimize_copy<InIt, FwdIt>::value;
|
||||||
return uninitialized_copy_n_dispatch(first, count, dest, containers_detail::bool_<do_optimized_copy>());
|
return uninitialized_copy_n_dispatch(first, count, dest, container_detail::bool_<do_optimized_copy>());
|
||||||
}
|
}
|
||||||
|
|
||||||
// uninitialized_copy_copy
|
// uninitialized_copy_copy
|
||||||
@@ -199,17 +167,17 @@ FwdIt uninitialized_copy_copy
|
|||||||
}
|
}
|
||||||
BOOST_CATCH(...){
|
BOOST_CATCH(...){
|
||||||
for(;result != mid; ++result){
|
for(;result != mid; ++result){
|
||||||
containers_detail::get_pointer(&*result)->~value_type();
|
container_detail::to_raw_pointer(&*result)->~value_type();
|
||||||
}
|
}
|
||||||
BOOST_RETHROW
|
BOOST_RETHROW
|
||||||
}
|
}
|
||||||
BOOST_CATCH_END
|
BOOST_CATCH_END
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_ALGORITHMS_HPP
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_ALGORITHMS_HPP
|
||||||
|
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
///////////////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_ALLOCATION_TYPE_HPP
|
#ifndef BOOST_CONTAINER_ALLOCATION_TYPE_HPP
|
||||||
#define BOOST_CONTAINERS_ALLOCATION_TYPE_HPP
|
#define BOOST_CONTAINER_ALLOCATION_TYPE_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -51,4 +51,4 @@ static const allocation_type zero_memory = (allocation_type)zero_memory_v
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //BOOST_CONTAINERS_ALLOCATION_TYPE_HPP
|
#endif //BOOST_CONTAINER_ALLOCATION_TYPE_HPP
|
||||||
|
@@ -7,15 +7,15 @@
|
|||||||
// See http://www.boost.org/libs/container for documentation.
|
// See http://www.boost.org/libs/container for documentation.
|
||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
#ifndef BOOST_CONTAINERS_CONTAINER_DETAIL_CONFIG_INCLUDED
|
#ifndef BOOST_CONTAINER_CONTAINER_DETAIL_CONFIG_INCLUDED
|
||||||
#define BOOST_CONTAINERS_CONTAINER_DETAIL_CONFIG_INCLUDED
|
#define BOOST_CONTAINER_CONTAINER_DETAIL_CONFIG_INCLUDED
|
||||||
#include <boost/config.hpp>
|
#include <boost/config.hpp>
|
||||||
|
|
||||||
#endif //BOOST_CONTAINERS_CONTAINER_DETAIL_CONFIG_INCLUDED
|
#endif //BOOST_CONTAINER_CONTAINER_DETAIL_CONFIG_INCLUDED
|
||||||
|
|
||||||
#ifdef BOOST_MSVC
|
#ifdef BOOST_MSVC
|
||||||
#ifndef _CRT_SECURE_NO_DEPRECATE
|
#ifndef _CRT_SECURE_NO_DEPRECATE
|
||||||
#define BOOST_CONTAINERS_DETAIL_CRT_SECURE_NO_DEPRECATE
|
#define BOOST_CONTAINER_DETAIL_CRT_SECURE_NO_DEPRECATE
|
||||||
#define _CRT_SECURE_NO_DEPRECATE
|
#define _CRT_SECURE_NO_DEPRECATE
|
||||||
#endif
|
#endif
|
||||||
#pragma warning (push)
|
#pragma warning (push)
|
||||||
|
@@ -9,8 +9,8 @@
|
|||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
#if defined BOOST_MSVC
|
#if defined BOOST_MSVC
|
||||||
#pragma warning (pop)
|
#pragma warning (pop)
|
||||||
#ifdef BOOST_CONTAINERS_DETAIL_CRT_SECURE_NO_DEPRECATE
|
#ifdef BOOST_CONTAINER_DETAIL_CRT_SECURE_NO_DEPRECATE
|
||||||
#undef BOOST_CONTAINERS_DETAIL_CRT_SECURE_NO_DEPRECATE
|
#undef BOOST_CONTAINER_DETAIL_CRT_SECURE_NO_DEPRECATE
|
||||||
#undef _CRT_SECURE_NO_DEPRECATE
|
#undef _CRT_SECURE_NO_DEPRECATE
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
@@ -10,8 +10,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DESTROYERS_HPP
|
#ifndef BOOST_CONTAINER_DESTROYERS_HPP
|
||||||
#define BOOST_CONTAINERS_DESTROYERS_HPP
|
#define BOOST_CONTAINER_DESTROYERS_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -21,18 +21,20 @@
|
|||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
#include <boost/container/detail/version_type.hpp>
|
#include <boost/container/detail/version_type.hpp>
|
||||||
#include <boost/container/detail/utilities.hpp>
|
#include <boost/container/detail/utilities.hpp>
|
||||||
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
//!A deleter for scoped_ptr that deallocates the memory
|
//!A deleter for scoped_ptr that deallocates the memory
|
||||||
//!allocated for an array of objects using a STL allocator.
|
//!allocated for an array of objects using a STL allocator.
|
||||||
template <class Allocator>
|
template <class Allocator>
|
||||||
struct scoped_array_deallocator
|
struct scoped_array_deallocator
|
||||||
{
|
{
|
||||||
typedef typename Allocator::pointer pointer;
|
typedef boost::container::allocator_traits<Allocator> AllocTraits;
|
||||||
typedef typename Allocator::size_type size_type;
|
typedef typename AllocTraits::pointer pointer;
|
||||||
|
typedef typename AllocTraits::size_type size_type;
|
||||||
|
|
||||||
scoped_array_deallocator(pointer p, Allocator& a, size_type length)
|
scoped_array_deallocator(pointer p, Allocator& a, size_type length)
|
||||||
: m_ptr(p), m_alloc(a), m_length(length) {}
|
: m_ptr(p), m_alloc(a), m_length(length) {}
|
||||||
@@ -52,8 +54,9 @@ struct scoped_array_deallocator
|
|||||||
template <class Allocator>
|
template <class Allocator>
|
||||||
struct null_scoped_array_deallocator
|
struct null_scoped_array_deallocator
|
||||||
{
|
{
|
||||||
typedef typename Allocator::pointer pointer;
|
typedef boost::container::allocator_traits<Allocator> AllocTraits;
|
||||||
typedef typename Allocator::size_type size_type;
|
typedef typename AllocTraits::pointer pointer;
|
||||||
|
typedef typename AllocTraits::size_type size_type;
|
||||||
|
|
||||||
null_scoped_array_deallocator(pointer, Allocator&, size_type)
|
null_scoped_array_deallocator(pointer, Allocator&, size_type)
|
||||||
{}
|
{}
|
||||||
@@ -68,15 +71,13 @@ struct null_scoped_array_deallocator
|
|||||||
template <class Allocator>
|
template <class Allocator>
|
||||||
struct scoped_destructor_n
|
struct scoped_destructor_n
|
||||||
{
|
{
|
||||||
typedef typename Allocator::pointer pointer;
|
typedef boost::container::allocator_traits<Allocator> AllocTraits;
|
||||||
typedef typename Allocator::value_type value_type;
|
typedef typename AllocTraits::pointer pointer;
|
||||||
typedef typename Allocator::size_type size_type;
|
typedef typename AllocTraits::value_type value_type;
|
||||||
|
typedef typename AllocTraits::size_type size_type;
|
||||||
|
|
||||||
pointer m_p;
|
scoped_destructor_n(pointer p, Allocator& a, size_type n)
|
||||||
size_type m_n;
|
: m_p(p), m_a(a), m_n(n)
|
||||||
|
|
||||||
scoped_destructor_n(pointer p, size_type n)
|
|
||||||
: m_p(p), m_n(n)
|
|
||||||
{}
|
{}
|
||||||
|
|
||||||
void release()
|
void release()
|
||||||
@@ -88,10 +89,15 @@ struct scoped_destructor_n
|
|||||||
~scoped_destructor_n()
|
~scoped_destructor_n()
|
||||||
{
|
{
|
||||||
if(!m_p) return;
|
if(!m_p) return;
|
||||||
value_type *raw_ptr = containers_detail::get_pointer(m_p);
|
value_type *raw_ptr = container_detail::to_raw_pointer(m_p);
|
||||||
for(size_type i = 0; i < m_n; ++i, ++raw_ptr)
|
for(size_type i = 0; i < m_n; ++i, ++raw_ptr)
|
||||||
raw_ptr->~value_type();
|
AllocTraits::destroy(m_a, raw_ptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
pointer m_p;
|
||||||
|
Allocator & m_a;
|
||||||
|
size_type m_n;
|
||||||
};
|
};
|
||||||
|
|
||||||
//!A deleter for scoped_ptr that destroys
|
//!A deleter for scoped_ptr that destroys
|
||||||
@@ -99,10 +105,11 @@ struct scoped_destructor_n
|
|||||||
template <class Allocator>
|
template <class Allocator>
|
||||||
struct null_scoped_destructor_n
|
struct null_scoped_destructor_n
|
||||||
{
|
{
|
||||||
typedef typename Allocator::pointer pointer;
|
typedef boost::container::allocator_traits<Allocator> AllocTraits;
|
||||||
typedef typename Allocator::size_type size_type;
|
typedef typename AllocTraits::pointer pointer;
|
||||||
|
typedef typename AllocTraits::size_type size_type;
|
||||||
|
|
||||||
null_scoped_destructor_n(pointer, size_type)
|
null_scoped_destructor_n(pointer, Allocator&, size_type)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
void increment_size(size_type)
|
void increment_size(size_type)
|
||||||
@@ -112,43 +119,45 @@ struct null_scoped_destructor_n
|
|||||||
{}
|
{}
|
||||||
};
|
};
|
||||||
|
|
||||||
template <class A>
|
template <class Allocator>
|
||||||
class allocator_destroyer
|
class allocator_destroyer
|
||||||
{
|
{
|
||||||
typedef typename A::value_type value_type;
|
typedef boost::container::allocator_traits<Allocator> AllocTraits;
|
||||||
typedef containers_detail::integral_constant<unsigned,
|
typedef typename AllocTraits::value_type value_type;
|
||||||
boost::container::containers_detail::
|
typedef typename AllocTraits::pointer pointer;
|
||||||
version<A>::value> alloc_version;
|
typedef container_detail::integral_constant<unsigned,
|
||||||
typedef containers_detail::integral_constant<unsigned, 1> allocator_v1;
|
boost::container::container_detail::
|
||||||
typedef containers_detail::integral_constant<unsigned, 2> allocator_v2;
|
version<Allocator>::value> alloc_version;
|
||||||
|
typedef container_detail::integral_constant<unsigned, 1> allocator_v1;
|
||||||
|
typedef container_detail::integral_constant<unsigned, 2> allocator_v2;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
A & a_;
|
Allocator & a_;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void priv_deallocate(const typename A::pointer &p, allocator_v1)
|
void priv_deallocate(const pointer &p, allocator_v1)
|
||||||
{ a_.deallocate(p, 1); }
|
{ AllocTraits::deallocate(a_,p, 1); }
|
||||||
|
|
||||||
void priv_deallocate(const typename A::pointer &p, allocator_v2)
|
void priv_deallocate(const pointer &p, allocator_v2)
|
||||||
{ a_.deallocate_one(p); }
|
{ a_.deallocate_one(p); }
|
||||||
|
|
||||||
public:
|
public:
|
||||||
allocator_destroyer(A &a)
|
allocator_destroyer(Allocator &a)
|
||||||
: a_(a)
|
: a_(a)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
void operator()(const typename A::pointer &p)
|
void operator()(const pointer &p)
|
||||||
{
|
{
|
||||||
containers_detail::get_pointer(p)->~value_type();
|
AllocTraits::destroy(a_, container_detail::to_raw_pointer(p));
|
||||||
priv_deallocate(p, alloc_version());
|
priv_deallocate(p, alloc_version());
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DESTROYERS_HPP
|
#endif //#ifndef BOOST_CONTAINER_DESTROYERS_HPP
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_FLAT_TREE_HPP
|
#ifndef BOOST_CONTAINER_FLAT_TREE_HPP
|
||||||
#define BOOST_CONTAINERS_FLAT_TREE_HPP
|
#define BOOST_CONTAINER_FLAT_TREE_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -37,7 +37,7 @@ namespace boost {
|
|||||||
|
|
||||||
namespace container {
|
namespace container {
|
||||||
|
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class Compare, class Value, class KeyOfValue>
|
template<class Compare, class Value, class KeyOfValue>
|
||||||
class flat_tree_value_compare
|
class flat_tree_value_compare
|
||||||
@@ -47,6 +47,10 @@ class flat_tree_value_compare
|
|||||||
typedef Value second_argument_type;
|
typedef Value second_argument_type;
|
||||||
typedef bool return_type;
|
typedef bool return_type;
|
||||||
public:
|
public:
|
||||||
|
flat_tree_value_compare()
|
||||||
|
: Compare()
|
||||||
|
{}
|
||||||
|
|
||||||
flat_tree_value_compare(const Compare &pred)
|
flat_tree_value_compare(const Compare &pred)
|
||||||
: Compare(pred)
|
: Compare(pred)
|
||||||
{}
|
{}
|
||||||
@@ -67,9 +71,9 @@ class flat_tree_value_compare
|
|||||||
template<class Pointer>
|
template<class Pointer>
|
||||||
struct get_flat_tree_iterators
|
struct get_flat_tree_iterators
|
||||||
{
|
{
|
||||||
typedef typename containers_detail::
|
typedef typename container_detail::
|
||||||
vector_iterator<Pointer> iterator;
|
vector_iterator<Pointer> iterator;
|
||||||
typedef typename containers_detail::
|
typedef typename container_detail::
|
||||||
vector_const_iterator<Pointer> const_iterator;
|
vector_const_iterator<Pointer> const_iterator;
|
||||||
typedef std::reverse_iterator<iterator> reverse_iterator;
|
typedef std::reverse_iterator<iterator> reverse_iterator;
|
||||||
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
||||||
@@ -90,23 +94,29 @@ class flat_tree
|
|||||||
//Inherit from value_compare to do EBO
|
//Inherit from value_compare to do EBO
|
||||||
: public value_compare
|
: public value_compare
|
||||||
{
|
{
|
||||||
private:
|
|
||||||
BOOST_COPYABLE_AND_MOVABLE(Data)
|
BOOST_COPYABLE_AND_MOVABLE(Data)
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
Data()
|
||||||
|
: value_compare(), m_vect()
|
||||||
|
{}
|
||||||
|
|
||||||
Data(const Data &d)
|
Data(const Data &d)
|
||||||
: value_compare(d), m_vect(d.m_vect)
|
: value_compare(d), m_vect(d.m_vect)
|
||||||
{}
|
{}
|
||||||
Data(const Compare &comp,
|
|
||||||
const vector_t &vect)
|
|
||||||
: value_compare(comp), m_vect(vect){}
|
|
||||||
|
|
||||||
Data(const value_compare &comp,
|
Data(BOOST_RV_REF(Data) d)
|
||||||
const vector_t &vect)
|
: value_compare(boost::move(d)), m_vect(boost::move(d.m_vect))
|
||||||
: value_compare(comp), m_vect(vect){}
|
{}
|
||||||
|
|
||||||
|
Data(const Compare &comp)
|
||||||
|
: value_compare(comp), m_vect()
|
||||||
|
{}
|
||||||
|
|
||||||
Data(const Compare &comp,
|
Data(const Compare &comp,
|
||||||
const allocator_t &alloc)
|
const allocator_t &alloc)
|
||||||
: value_compare(comp), m_vect(alloc){}
|
: value_compare(comp), m_vect(alloc)
|
||||||
|
{}
|
||||||
|
|
||||||
Data& operator=(BOOST_COPY_ASSIGN_REF(Data) d)
|
Data& operator=(BOOST_COPY_ASSIGN_REF(Data) d)
|
||||||
{
|
{
|
||||||
@@ -122,6 +132,13 @@ class flat_tree
|
|||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void swap(Data &d)
|
||||||
|
{
|
||||||
|
value_compare& mycomp = *this, & othercomp = d;
|
||||||
|
container_detail::do_swap(mycomp, othercomp);
|
||||||
|
this->m_vect.swap(d.m_vect);
|
||||||
|
}
|
||||||
|
|
||||||
vector_t m_vect;
|
vector_t m_vect;
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -138,23 +155,30 @@ class flat_tree
|
|||||||
typedef Key key_type;
|
typedef Key key_type;
|
||||||
typedef Compare key_compare;
|
typedef Compare key_compare;
|
||||||
typedef typename vector_t::allocator_type allocator_type;
|
typedef typename vector_t::allocator_type allocator_type;
|
||||||
typedef allocator_type stored_allocator_type;
|
typedef typename vector_t::size_type size_type;
|
||||||
typedef typename allocator_type::size_type size_type;
|
typedef typename vector_t::difference_type difference_type;
|
||||||
typedef typename allocator_type::difference_type difference_type;
|
|
||||||
typedef typename vector_t::iterator iterator;
|
typedef typename vector_t::iterator iterator;
|
||||||
typedef typename vector_t::const_iterator const_iterator;
|
typedef typename vector_t::const_iterator const_iterator;
|
||||||
typedef std::reverse_iterator<iterator> reverse_iterator;
|
typedef typename vector_t::reverse_iterator reverse_iterator;
|
||||||
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
typedef typename vector_t::const_reverse_iterator const_reverse_iterator;
|
||||||
|
|
||||||
|
|
||||||
// allocation/deallocation
|
//!Standard extension
|
||||||
flat_tree(const Compare& comp = Compare(),
|
typedef allocator_type stored_allocator_type;
|
||||||
const allocator_type& a = allocator_type())
|
|
||||||
|
flat_tree()
|
||||||
|
: m_data()
|
||||||
|
{ }
|
||||||
|
|
||||||
|
explicit flat_tree(const Compare& comp)
|
||||||
|
: m_data(comp)
|
||||||
|
{ }
|
||||||
|
|
||||||
|
flat_tree(const Compare& comp, const allocator_type& a)
|
||||||
: m_data(comp, a)
|
: m_data(comp, a)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
flat_tree(const flat_tree& x)
|
flat_tree(const flat_tree& x)
|
||||||
: m_data(x.m_data, x.m_data.m_vect)
|
: m_data(x.m_data)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
flat_tree(BOOST_RV_REF(flat_tree) x)
|
flat_tree(BOOST_RV_REF(flat_tree) x)
|
||||||
@@ -237,14 +261,7 @@ class flat_tree
|
|||||||
{ return this->m_data.m_vect.max_size(); }
|
{ return this->m_data.m_vect.max_size(); }
|
||||||
|
|
||||||
void swap(flat_tree& other)
|
void swap(flat_tree& other)
|
||||||
{
|
{ this->m_data.swap(other.m_data); }
|
||||||
value_compare& mycomp = this->m_data;
|
|
||||||
value_compare& othercomp = other.m_data;
|
|
||||||
containers_detail::do_swap(mycomp, othercomp);
|
|
||||||
vector_t & myvect = this->m_data.m_vect;
|
|
||||||
vector_t & othervect = other.m_data.m_vect;
|
|
||||||
myvect.swap(othervect);
|
|
||||||
}
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
// insert/erase
|
// insert/erase
|
||||||
@@ -332,7 +349,7 @@ class flat_tree
|
|||||||
priv_insert_equal(first, last, ItCat());
|
priv_insert_equal(first, last, ItCat());
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
template <class... Args>
|
template <class... Args>
|
||||||
iterator emplace_unique(Args&&... args)
|
iterator emplace_unique(Args&&... args)
|
||||||
@@ -377,100 +394,69 @@ class flat_tree
|
|||||||
return priv_insert_commit(data, boost::move(val));
|
return priv_insert_commit(data, boost::move(val));
|
||||||
}
|
}
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator emplace_unique()
|
|
||||||
{
|
|
||||||
containers_detail::value_init<value_type> vval;
|
|
||||||
value_type &val = vval.m_t;
|
|
||||||
insert_commit_data data;
|
|
||||||
std::pair<iterator,bool> ret =
|
|
||||||
priv_insert_unique_prepare(val, data);
|
|
||||||
if(ret.second){
|
|
||||||
ret.first = priv_insert_commit(data, boost::move(val));
|
|
||||||
}
|
|
||||||
return ret.first;
|
|
||||||
}
|
|
||||||
|
|
||||||
iterator emplace_hint_unique(const_iterator hint)
|
|
||||||
{
|
|
||||||
containers_detail::value_init<value_type> vval;
|
|
||||||
value_type &val = vval.m_t;
|
|
||||||
insert_commit_data data;
|
|
||||||
std::pair<iterator,bool> ret = priv_insert_unique_prepare(hint, val, data);
|
|
||||||
if(ret.second){
|
|
||||||
ret.first = priv_insert_commit(data, boost::move(val));
|
|
||||||
}
|
|
||||||
return ret.first;
|
|
||||||
}
|
|
||||||
|
|
||||||
iterator emplace_equal()
|
|
||||||
{
|
|
||||||
containers_detail::value_init<value_type> vval;
|
|
||||||
value_type &val = vval.m_t;
|
|
||||||
iterator i = this->upper_bound(KeyOfValue()(val));
|
|
||||||
i = this->m_data.m_vect.insert(i, boost::move(val));
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
|
|
||||||
iterator emplace_hint_equal(const_iterator hint)
|
|
||||||
{
|
|
||||||
containers_detail::value_init<value_type> vval;
|
|
||||||
value_type &val = vval.m_t;
|
|
||||||
insert_commit_data data;
|
|
||||||
priv_insert_equal_prepare(hint, val, data);
|
|
||||||
return priv_insert_commit(data, boost::move(val));
|
|
||||||
}
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
iterator emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
value_type val(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
BOOST_PP_EXPR_IF(BOOST_PP_NOT(n), container_detail::value_init<) value_type \
|
||||||
|
BOOST_PP_EXPR_IF(BOOST_PP_NOT(n), >) vval BOOST_PP_LPAREN_IF(n) \
|
||||||
|
BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) BOOST_PP_RPAREN_IF(n); \
|
||||||
|
value_type &val = vval; \
|
||||||
insert_commit_data data; \
|
insert_commit_data data; \
|
||||||
std::pair<iterator,bool> ret = priv_insert_unique_prepare(val, data); \
|
std::pair<iterator,bool> ret = priv_insert_unique_prepare(val, data); \
|
||||||
if(ret.second){ \
|
if(ret.second){ \
|
||||||
ret.first = priv_insert_commit(data, boost::move(val)); \
|
ret.first = priv_insert_commit(data, boost::move(val)); \
|
||||||
} \
|
} \
|
||||||
return ret.first; \
|
return ret.first; \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_hint_unique(const_iterator hint, \
|
iterator emplace_hint_unique(const_iterator hint \
|
||||||
BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
value_type val(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
BOOST_PP_EXPR_IF(BOOST_PP_NOT(n), container_detail::value_init<) value_type \
|
||||||
|
BOOST_PP_EXPR_IF(BOOST_PP_NOT(n), >) vval BOOST_PP_LPAREN_IF(n) \
|
||||||
|
BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) BOOST_PP_RPAREN_IF(n); \
|
||||||
|
value_type &val = vval; \
|
||||||
insert_commit_data data; \
|
insert_commit_data data; \
|
||||||
std::pair<iterator,bool> ret = priv_insert_unique_prepare(hint, val, data); \
|
std::pair<iterator,bool> ret = priv_insert_unique_prepare(hint, val, data); \
|
||||||
if(ret.second){ \
|
if(ret.second){ \
|
||||||
ret.first = priv_insert_commit(data, boost::move(val)); \
|
ret.first = priv_insert_commit(data, boost::move(val)); \
|
||||||
} \
|
} \
|
||||||
return ret.first; \
|
return ret.first; \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
iterator emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
value_type val(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
BOOST_PP_EXPR_IF(BOOST_PP_NOT(n), container_detail::value_init<) value_type \
|
||||||
|
BOOST_PP_EXPR_IF(BOOST_PP_NOT(n), >) vval BOOST_PP_LPAREN_IF(n) \
|
||||||
|
BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) BOOST_PP_RPAREN_IF(n); \
|
||||||
|
value_type &val = vval; \
|
||||||
iterator i = this->upper_bound(KeyOfValue()(val)); \
|
iterator i = this->upper_bound(KeyOfValue()(val)); \
|
||||||
i = this->m_data.m_vect.insert(i, boost::move(val)); \
|
i = this->m_data.m_vect.insert(i, boost::move(val)); \
|
||||||
return i; \
|
return i; \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_hint_equal(const_iterator hint, \
|
iterator emplace_hint_equal(const_iterator hint \
|
||||||
BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
value_type val(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
BOOST_PP_EXPR_IF(BOOST_PP_NOT(n), container_detail::value_init<) value_type \
|
||||||
|
BOOST_PP_EXPR_IF(BOOST_PP_NOT(n), >) vval BOOST_PP_LPAREN_IF(n) \
|
||||||
|
BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) BOOST_PP_RPAREN_IF(n); \
|
||||||
|
value_type &val = vval; \
|
||||||
insert_commit_data data; \
|
insert_commit_data data; \
|
||||||
priv_insert_equal_prepare(hint, val, data); \
|
priv_insert_equal_prepare(hint, val, data); \
|
||||||
return priv_insert_commit(data, boost::move(val)); \
|
return priv_insert_commit(data, boost::move(val)); \
|
||||||
} \
|
} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator erase(const_iterator position)
|
iterator erase(const_iterator position)
|
||||||
{ return this->m_data.m_vect.erase(position); }
|
{ return this->m_data.m_vect.erase(position); }
|
||||||
@@ -571,8 +557,6 @@ class flat_tree
|
|||||||
// insert val before pos
|
// insert val before pos
|
||||||
// else
|
// else
|
||||||
// insert val before upper_bound(val)
|
// insert val before upper_bound(val)
|
||||||
// else if pos+1 == end || val <= *(pos+1)
|
|
||||||
// insert val after pos
|
|
||||||
// else
|
// else
|
||||||
// insert val before lower_bound(val)
|
// insert val before lower_bound(val)
|
||||||
const value_compare &value_comp = this->m_data;
|
const value_compare &value_comp = this->m_data;
|
||||||
@@ -586,10 +570,6 @@ class flat_tree
|
|||||||
this->priv_upper_bound(this->cbegin(), pos, KeyOfValue()(val));
|
this->priv_upper_bound(this->cbegin(), pos, KeyOfValue()(val));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
//Works, but increases code complexity
|
|
||||||
//else if (++pos == this->end() || !value_comp(*pos, val)){
|
|
||||||
// return this->m_data.m_vect.insert(pos, val);
|
|
||||||
//}
|
|
||||||
else{
|
else{
|
||||||
data.position =
|
data.position =
|
||||||
this->priv_lower_bound(pos, this->cend(), KeyOfValue()(val));
|
this->priv_lower_bound(pos, this->cend(), KeyOfValue()(val));
|
||||||
@@ -838,7 +818,7 @@ swap(flat_tree<Key,Value,KeyOfValue,Compare,A>& x,
|
|||||||
flat_tree<Key,Value,KeyOfValue,Compare,A>& y)
|
flat_tree<Key,Value,KeyOfValue,Compare,A>& y)
|
||||||
{ x.swap(y); }
|
{ x.swap(y); }
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
|
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
/*
|
/*
|
||||||
@@ -846,7 +826,7 @@ swap(flat_tree<Key,Value,KeyOfValue,Compare,A>& x,
|
|||||||
//!specialization for optimizations
|
//!specialization for optimizations
|
||||||
template <class K, class V, class KOV,
|
template <class K, class V, class KOV,
|
||||||
class C, class A>
|
class C, class A>
|
||||||
struct has_trivial_destructor_after_move<boost::container::containers_detail::flat_tree<K, V, KOV, C, A> >
|
struct has_trivial_destructor_after_move<boost::container::container_detail::flat_tree<K, V, KOV, C, A> >
|
||||||
{
|
{
|
||||||
static const bool value = has_trivial_destructor<A>::value && has_trivial_destructor<C>::value;
|
static const bool value = has_trivial_destructor<A>::value && has_trivial_destructor<C>::value;
|
||||||
};
|
};
|
||||||
@@ -855,4 +835,4 @@ struct has_trivial_destructor_after_move<boost::container::containers_detail::fl
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif // BOOST_CONTAINERS_FLAT_TREE_HPP
|
#endif // BOOST_CONTAINER_FLAT_TREE_HPP
|
||||||
|
88
include/boost/container/detail/function_detector.hpp
Normal file
88
include/boost/container/detail/function_detector.hpp
Normal file
@@ -0,0 +1,88 @@
|
|||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// (C) Copyright Ion Gaztanaga 2009-2011.
|
||||||
|
//
|
||||||
|
// Distributed under the Boost Software License, Version 1.0.
|
||||||
|
// (See accompanying file LICENSE_1_0.txt or copy at
|
||||||
|
// http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
//
|
||||||
|
// See http://www.boost.org/libs/container for documentation.
|
||||||
|
//
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
// This code was modified from the code posted by Alexandre Courpron in his
|
||||||
|
// article "Interface Detection" in The Code Project:
|
||||||
|
// http://www.codeproject.com/KB/architecture/Detector.aspx
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Copyright 2007 Alexandre Courpron
|
||||||
|
//
|
||||||
|
// Permission to use, copy, modify, redistribute and sell this software,
|
||||||
|
// provided that this copyright notice appears on all copies of the software.
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
#ifndef BOOST_CONTAINER_DETAIL_FUNCTION_DETECTOR_HPP
|
||||||
|
#define BOOST_CONTAINER_DETAIL_FUNCTION_DETECTOR_HPP
|
||||||
|
|
||||||
|
#include <boost/container/detail/config_begin.hpp>
|
||||||
|
|
||||||
|
namespace boost {
|
||||||
|
namespace container {
|
||||||
|
namespace function_detector {
|
||||||
|
|
||||||
|
typedef char NotFoundType;
|
||||||
|
struct StaticFunctionType { NotFoundType x [2]; };
|
||||||
|
struct NonStaticFunctionType { NotFoundType x [3]; };
|
||||||
|
|
||||||
|
enum
|
||||||
|
{ NotFound = 0,
|
||||||
|
StaticFunction = sizeof( StaticFunctionType ) - sizeof( NotFoundType ),
|
||||||
|
NonStaticFunction = sizeof( NonStaticFunctionType ) - sizeof( NotFoundType )
|
||||||
|
};
|
||||||
|
|
||||||
|
} //namespace boost {
|
||||||
|
} //namespace container {
|
||||||
|
} //namespace function_detector {
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_CREATE_FUNCTION_DETECTOR(Identifier, InstantiationKey) \
|
||||||
|
namespace boost { \
|
||||||
|
namespace container { \
|
||||||
|
namespace function_detector { \
|
||||||
|
template < class T, \
|
||||||
|
class NonStaticType, \
|
||||||
|
class NonStaticConstType, \
|
||||||
|
class StaticType > \
|
||||||
|
class DetectMember_##InstantiationKey_##Identifier { \
|
||||||
|
template < NonStaticType > \
|
||||||
|
struct TestNonStaticNonConst ; \
|
||||||
|
\
|
||||||
|
template < NonStaticConstType > \
|
||||||
|
struct TestNonStaticConst ; \
|
||||||
|
\
|
||||||
|
template < StaticType > \
|
||||||
|
struct TestStatic ; \
|
||||||
|
\
|
||||||
|
template <class U > \
|
||||||
|
static NonStaticFunctionType Test( TestNonStaticNonConst<&U::Identifier>*, int ); \
|
||||||
|
\
|
||||||
|
template <class U > \
|
||||||
|
static NonStaticFunctionType Test( TestNonStaticConst<&U::Identifier>*, int ); \
|
||||||
|
\
|
||||||
|
template <class U> \
|
||||||
|
static StaticFunctionType Test( TestStatic<&U::Identifier>*, int ); \
|
||||||
|
\
|
||||||
|
template <class U> \
|
||||||
|
static NotFoundType Test( ... ); \
|
||||||
|
public : \
|
||||||
|
static const int check = NotFound + (sizeof(Test<T>(0, 0)) - sizeof(NotFoundType));\
|
||||||
|
};\
|
||||||
|
}}} //namespace boost::container::function_detector {
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_DETECT_FUNCTION(Class, InstantiationKey, ReturnType, Identifier, Params) \
|
||||||
|
::boost::container::function_detector::DetectMember_##InstantiationKey_##Identifier< Class,\
|
||||||
|
ReturnType (Class::*)Params,\
|
||||||
|
ReturnType (Class::*)Params const,\
|
||||||
|
ReturnType (*)Params \
|
||||||
|
>::check
|
||||||
|
|
||||||
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
|
#endif //@ifndef BOOST_CONTAINER_DETAIL_FUNCTION_DETECTOR_HPP
|
@@ -11,8 +11,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_ITERATORS_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_ITERATORS_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_ITERATORS_HPP
|
#define BOOST_CONTAINER_DETAIL_ITERATORS_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -21,8 +21,9 @@
|
|||||||
#include "config_begin.hpp"
|
#include "config_begin.hpp"
|
||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
|
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
#include <boost/container/detail/variadic_templates_tools.hpp>
|
#include <boost/container/detail/variadic_templates_tools.hpp>
|
||||||
#include <boost/container/detail/stored_ref.hpp>
|
#include <boost/container/detail/stored_ref.hpp>
|
||||||
#else
|
#else
|
||||||
@@ -368,7 +369,7 @@ class repeat_iterator
|
|||||||
{ return m_num - other.m_num; }
|
{ return m_num - other.m_num; }
|
||||||
};
|
};
|
||||||
|
|
||||||
template <class T, class E, class Difference /*= std::ptrdiff_t*/>
|
template <class T, class EmplaceFunctor, class Difference /*= std::ptrdiff_t*/>
|
||||||
class emplace_iterator
|
class emplace_iterator
|
||||||
: public std::iterator
|
: public std::iterator
|
||||||
<std::random_access_iterator_tag, T, Difference, const T*, const T &>
|
<std::random_access_iterator_tag, T, Difference, const T*, const T &>
|
||||||
@@ -377,7 +378,7 @@ class emplace_iterator
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
typedef Difference difference_type;
|
typedef Difference difference_type;
|
||||||
explicit emplace_iterator(E&e)
|
explicit emplace_iterator(EmplaceFunctor&e)
|
||||||
: m_num(1), m_pe(&e){}
|
: m_num(1), m_pe(&e){}
|
||||||
|
|
||||||
emplace_iterator()
|
emplace_iterator()
|
||||||
@@ -453,12 +454,13 @@ class emplace_iterator
|
|||||||
const T* operator->() const
|
const T* operator->() const
|
||||||
{ return &(dereference()); }
|
{ return &(dereference()); }
|
||||||
|
|
||||||
void construct_in_place(T* ptr)
|
template<class A>
|
||||||
{ (*m_pe)(ptr); }
|
void construct_in_place(A &a, T* ptr)
|
||||||
|
{ (*m_pe)(a, ptr); }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
difference_type m_num;
|
difference_type m_num;
|
||||||
E * m_pe;
|
EmplaceFunctor * m_pe;
|
||||||
|
|
||||||
void increment()
|
void increment()
|
||||||
{ --m_num; }
|
{ --m_num; }
|
||||||
@@ -485,54 +487,54 @@ class emplace_iterator
|
|||||||
{ return difference_type(m_num - other.m_num); }
|
{ return difference_type(m_num - other.m_num); }
|
||||||
};
|
};
|
||||||
|
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
template<class T, class ...Args>
|
template<class ...Args>
|
||||||
struct emplace_functor
|
struct emplace_functor
|
||||||
{
|
{
|
||||||
typedef typename containers_detail::build_number_seq<sizeof...(Args)>::type index_tuple_t;
|
typedef typename container_detail::build_number_seq<sizeof...(Args)>::type index_tuple_t;
|
||||||
|
|
||||||
emplace_functor(Args&&... args)
|
emplace_functor(Args&&... args)
|
||||||
: args_(args...)
|
: args_(args...)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
void operator()(T *ptr)
|
template<class A, class T>
|
||||||
{ emplace_functor::inplace_impl(ptr, index_tuple_t()); }
|
void operator()(A &a, T *ptr)
|
||||||
|
{ emplace_functor::inplace_impl(a, ptr, index_tuple_t()); }
|
||||||
|
|
||||||
template<int ...IdxPack>
|
template<class A, class T, int ...IdxPack>
|
||||||
void inplace_impl(T* ptr, const containers_detail::index_tuple<IdxPack...>&)
|
void inplace_impl(A &a, T* ptr, const container_detail::index_tuple<IdxPack...>&)
|
||||||
{ ::new(ptr) T(containers_detail::stored_ref<Args>::forward(containers_detail::get<IdxPack>(args_))...); }
|
{
|
||||||
|
allocator_traits<A>::construct
|
||||||
|
(a, ptr, container_detail::stored_ref<Args>::forward
|
||||||
|
(container_detail::get<IdxPack>(args_))...);
|
||||||
|
}
|
||||||
|
|
||||||
containers_detail::tuple<Args&...> args_;
|
container_detail::tuple<Args&...> args_;
|
||||||
};
|
};
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
|
||||||
template<class T>
|
|
||||||
struct emplace_functor
|
|
||||||
{
|
|
||||||
emplace_functor()
|
|
||||||
{}
|
|
||||||
void operator()(T *ptr)
|
|
||||||
{ new(ptr) T(); }
|
|
||||||
};
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template <class T, BOOST_PP_ENUM_PARAMS(n, class P) > \
|
BOOST_PP_EXPR_IF(n, template <) \
|
||||||
|
BOOST_PP_ENUM_PARAMS(n, class P) \
|
||||||
|
BOOST_PP_EXPR_IF(n, >) \
|
||||||
struct BOOST_PP_CAT(BOOST_PP_CAT(emplace_functor, n), arg) \
|
struct BOOST_PP_CAT(BOOST_PP_CAT(emplace_functor, n), arg) \
|
||||||
{ \
|
{ \
|
||||||
BOOST_PP_CAT(BOOST_PP_CAT(emplace_functor, n), arg) \
|
BOOST_PP_CAT(BOOST_PP_CAT(emplace_functor, n), arg) \
|
||||||
( BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _) ) \
|
( BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _) ) \
|
||||||
: BOOST_PP_ENUM(n, BOOST_CONTAINERS_AUX_PARAM_INIT, _) {} \
|
BOOST_PP_EXPR_IF(n, :) BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_INIT, _){} \
|
||||||
\
|
\
|
||||||
void operator()(T *ptr) \
|
template<class A, class T> \
|
||||||
|
void operator()(A &a, T *ptr) \
|
||||||
{ \
|
{ \
|
||||||
new(ptr)T (BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_MEMBER_FORWARD, _)); \
|
allocator_traits<A>::construct \
|
||||||
|
(a, ptr BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_MEMBER_FORWARD, _) );\
|
||||||
} \
|
} \
|
||||||
BOOST_PP_REPEAT(n, BOOST_CONTAINERS_AUX_PARAM_DEFINE, _) \
|
BOOST_PP_REPEAT(n, BOOST_CONTAINER_PP_PARAM_DEFINE, _) \
|
||||||
}; \
|
}; \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
@@ -542,5 +544,5 @@ struct emplace_functor
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_ITERATORS_HPP
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_ITERATORS_HPP
|
||||||
|
|
||||||
|
@@ -22,7 +22,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
// Greatest common divisor and least common multiple
|
// Greatest common divisor and least common multiple
|
||||||
|
|
||||||
@@ -104,7 +104,7 @@ inline std::size_t floor_log2 (std::size_t x)
|
|||||||
return log2;
|
return log2;
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace containers_detail
|
} // namespace container_detail
|
||||||
} // namespace container
|
} // namespace container
|
||||||
} // namespace boost
|
} // namespace boost
|
||||||
|
|
||||||
|
@@ -10,8 +10,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_CONTAINER_DETAIL_MPL_HPP
|
#ifndef BOOST_CONTAINER_CONTAINER_DETAIL_MPL_HPP
|
||||||
#define BOOST_CONTAINERS_CONTAINER_DETAIL_MPL_HPP
|
#define BOOST_CONTAINER_CONTAINER_DETAIL_MPL_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -21,7 +21,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template <class T, T val>
|
template <class T, T val>
|
||||||
struct integral_constant
|
struct integral_constant
|
||||||
@@ -34,6 +34,7 @@ template< bool C_ >
|
|||||||
struct bool_ : integral_constant<bool, C_>
|
struct bool_ : integral_constant<bool, C_>
|
||||||
{
|
{
|
||||||
static const bool value = C_;
|
static const bool value = C_;
|
||||||
|
operator bool() const { return bool_::value; }
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef bool_<true> true_;
|
typedef bool_<true> true_;
|
||||||
@@ -147,9 +148,9 @@ struct ls_zeros<1>
|
|||||||
static const std::size_t value = 0;
|
static const std::size_t value = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_CONTAINER_DETAIL_MPL_HPP
|
#endif //#ifndef BOOST_CONTAINER_CONTAINER_DETAIL_MPL_HPP
|
||||||
|
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_MULTIALLOCATION_CHAIN_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_MULTIALLOCATION_CHAIN_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_MULTIALLOCATION_CHAIN_HPP
|
#define BOOST_CONTAINER_DETAIL_MULTIALLOCATION_CHAIN_HPP
|
||||||
|
|
||||||
#include "config_begin.hpp"
|
#include "config_begin.hpp"
|
||||||
#include <boost/container/container_fwd.hpp>
|
#include <boost/container/container_fwd.hpp>
|
||||||
@@ -17,13 +17,13 @@
|
|||||||
#include <boost/container/detail/type_traits.hpp>
|
#include <boost/container/detail/type_traits.hpp>
|
||||||
#include <boost/container/detail/transform_iterator.hpp>
|
#include <boost/container/detail/transform_iterator.hpp>
|
||||||
#include <boost/intrusive/slist.hpp>
|
#include <boost/intrusive/slist.hpp>
|
||||||
#include <boost/pointer_to_other.hpp>
|
#include <boost/intrusive/pointer_traits.hpp>
|
||||||
#include <boost/type_traits/make_unsigned.hpp>
|
#include <boost/type_traits/make_unsigned.hpp>
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class VoidPointer>
|
template<class VoidPointer>
|
||||||
class basic_multiallocation_chain
|
class basic_multiallocation_chain
|
||||||
@@ -33,8 +33,10 @@ class basic_multiallocation_chain
|
|||||||
,bi::link_mode<bi::normal_link>
|
,bi::link_mode<bi::normal_link>
|
||||||
> node;
|
> node;
|
||||||
|
|
||||||
typedef typename boost::pointer_to_other<VoidPointer, char>::type char_ptr;
|
typedef typename boost::intrusive::pointer_traits
|
||||||
typedef typename std::iterator_traits<char_ptr>::difference_type difference_type;
|
<VoidPointer>::template rebind_pointer<char>::type char_ptr;
|
||||||
|
typedef typename boost::intrusive::
|
||||||
|
pointer_traits<char_ptr>::difference_type difference_type;
|
||||||
|
|
||||||
typedef bi::slist< node
|
typedef bi::slist< node
|
||||||
, bi::linear<true>
|
, bi::linear<true>
|
||||||
@@ -44,7 +46,7 @@ class basic_multiallocation_chain
|
|||||||
slist_impl_t slist_impl_;
|
slist_impl_t slist_impl_;
|
||||||
|
|
||||||
static node & to_node(VoidPointer p)
|
static node & to_node(VoidPointer p)
|
||||||
{ return *static_cast<node*>(static_cast<void*>(containers_detail::get_pointer(p))); }
|
{ return *static_cast<node*>(static_cast<void*>(container_detail::to_raw_pointer(p))); }
|
||||||
|
|
||||||
BOOST_MOVABLE_BUT_NOT_COPYABLE(basic_multiallocation_chain)
|
BOOST_MOVABLE_BUT_NOT_COPYABLE(basic_multiallocation_chain)
|
||||||
|
|
||||||
@@ -140,7 +142,7 @@ class basic_multiallocation_chain
|
|||||||
template<class T>
|
template<class T>
|
||||||
struct cast_functor
|
struct cast_functor
|
||||||
{
|
{
|
||||||
typedef typename containers_detail::add_reference<T>::type result_type;
|
typedef typename container_detail::add_reference<T>::type result_type;
|
||||||
template<class U>
|
template<class U>
|
||||||
result_type operator()(U &ptr) const
|
result_type operator()(U &ptr) const
|
||||||
{ return *static_cast<T*>(static_cast<void*>(&ptr)); }
|
{ return *static_cast<T*>(static_cast<void*>(&ptr)); }
|
||||||
@@ -154,18 +156,18 @@ class transform_multiallocation_chain
|
|||||||
|
|
||||||
MultiallocationChain holder_;
|
MultiallocationChain holder_;
|
||||||
typedef typename MultiallocationChain::void_pointer void_pointer;
|
typedef typename MultiallocationChain::void_pointer void_pointer;
|
||||||
typedef typename boost::pointer_to_other
|
typedef typename boost::intrusive::pointer_traits
|
||||||
<void_pointer, T>::type pointer;
|
<void_pointer>::template rebind_pointer<T>::type pointer;
|
||||||
|
|
||||||
static pointer cast(void_pointer p)
|
static pointer cast(void_pointer p)
|
||||||
{
|
{
|
||||||
return pointer(static_cast<T*>(containers_detail::get_pointer(p)));
|
return pointer(static_cast<T*>(container_detail::to_raw_pointer(p)));
|
||||||
}
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
typedef transform_iterator
|
typedef transform_iterator
|
||||||
< typename MultiallocationChain::iterator
|
< typename MultiallocationChain::iterator
|
||||||
, containers_detail::cast_functor <T> > iterator;
|
, container_detail::cast_functor <T> > iterator;
|
||||||
typedef typename MultiallocationChain::size_type size_type;
|
typedef typename MultiallocationChain::size_type size_type;
|
||||||
|
|
||||||
transform_multiallocation_chain()
|
transform_multiallocation_chain()
|
||||||
@@ -243,10 +245,10 @@ class transform_multiallocation_chain
|
|||||||
|
|
||||||
}}}
|
}}}
|
||||||
|
|
||||||
// namespace containers_detail {
|
// namespace container_detail {
|
||||||
// namespace container {
|
// namespace container {
|
||||||
// namespace boost {
|
// namespace boost {
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //BOOST_CONTAINERS_DETAIL_MULTIALLOCATION_CHAIN_HPP
|
#endif //BOOST_CONTAINER_DETAIL_MULTIALLOCATION_CHAIN_HPP
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_NODE_ALLOC_HPP_
|
#ifndef BOOST_CONTAINER_DETAIL_NODE_ALLOC_HPP_
|
||||||
#define BOOST_CONTAINERS_DETAIL_NODE_ALLOC_HPP_
|
#define BOOST_CONTAINER_DETAIL_NODE_ALLOC_HPP_
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -27,10 +27,11 @@
|
|||||||
#include <boost/container/detail/version_type.hpp>
|
#include <boost/container/detail/version_type.hpp>
|
||||||
#include <boost/container/detail/type_traits.hpp>
|
#include <boost/container/detail/type_traits.hpp>
|
||||||
#include <boost/container/detail/utilities.hpp>
|
#include <boost/container/detail/utilities.hpp>
|
||||||
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
#include <boost/container/detail/mpl.hpp>
|
#include <boost/container/detail/mpl.hpp>
|
||||||
#include <boost/container/detail/destroyers.hpp>
|
#include <boost/container/detail/destroyers.hpp>
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
#include <boost/container/detail/preprocessor.hpp>
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -39,19 +40,20 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
//!A deleter for scoped_ptr that deallocates the memory
|
//!A deleter for scoped_ptr that deallocates the memory
|
||||||
//!allocated for an object using a STL allocator.
|
//!allocated for an object using a STL allocator.
|
||||||
template <class Allocator>
|
template <class A>
|
||||||
struct scoped_deallocator
|
struct scoped_deallocator
|
||||||
{
|
{
|
||||||
typedef typename Allocator::pointer pointer;
|
typedef allocator_traits<A> allocator_traits_type;
|
||||||
typedef containers_detail::integral_constant<unsigned,
|
typedef typename allocator_traits_type::pointer pointer;
|
||||||
boost::container::containers_detail::
|
typedef container_detail::integral_constant<unsigned,
|
||||||
version<Allocator>::value> alloc_version;
|
boost::container::container_detail::
|
||||||
typedef containers_detail::integral_constant<unsigned, 1> allocator_v1;
|
version<A>::value> alloc_version;
|
||||||
typedef containers_detail::integral_constant<unsigned, 2> allocator_v2;
|
typedef container_detail::integral_constant<unsigned, 1> allocator_v1;
|
||||||
|
typedef container_detail::integral_constant<unsigned, 2> allocator_v2;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void priv_deallocate(allocator_v1)
|
void priv_deallocate(allocator_v1)
|
||||||
@@ -65,9 +67,9 @@ struct scoped_deallocator
|
|||||||
public:
|
public:
|
||||||
|
|
||||||
pointer m_ptr;
|
pointer m_ptr;
|
||||||
Allocator& m_alloc;
|
A& m_alloc;
|
||||||
|
|
||||||
scoped_deallocator(pointer p, Allocator& a)
|
scoped_deallocator(pointer p, A& a)
|
||||||
: m_ptr(p), m_alloc(a)
|
: m_ptr(p), m_alloc(a)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
@@ -88,7 +90,8 @@ struct scoped_deallocator
|
|||||||
template <class A>
|
template <class A>
|
||||||
class allocator_destroyer_and_chain_builder
|
class allocator_destroyer_and_chain_builder
|
||||||
{
|
{
|
||||||
typedef typename A::value_type value_type;
|
typedef allocator_traits<A> allocator_traits_type;
|
||||||
|
typedef typename allocator_traits_type::value_type value_type;
|
||||||
typedef typename A::multiallocation_chain multiallocation_chain;
|
typedef typename A::multiallocation_chain multiallocation_chain;
|
||||||
|
|
||||||
A & a_;
|
A & a_;
|
||||||
@@ -100,17 +103,17 @@ class allocator_destroyer_and_chain_builder
|
|||||||
{}
|
{}
|
||||||
|
|
||||||
void operator()(const typename A::pointer &p)
|
void operator()(const typename A::pointer &p)
|
||||||
{
|
{
|
||||||
value_type *vp = containers_detail::get_pointer(p);
|
allocator_traits<A>::destroy(a_, container_detail::to_raw_pointer(p));
|
||||||
vp->~value_type();
|
c_.push_front(p);
|
||||||
c_.push_front(vp);
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
template <class A>
|
template <class A>
|
||||||
class allocator_multialloc_chain_node_deallocator
|
class allocator_multialloc_chain_node_deallocator
|
||||||
{
|
{
|
||||||
typedef typename A::value_type value_type;
|
typedef allocator_traits<A> allocator_traits_type;
|
||||||
|
typedef typename allocator_traits_type::value_type value_type;
|
||||||
typedef typename A::multiallocation_chain multiallocation_chain;
|
typedef typename A::multiallocation_chain multiallocation_chain;
|
||||||
typedef allocator_destroyer_and_chain_builder<A> chain_builder;
|
typedef allocator_destroyer_and_chain_builder<A> chain_builder;
|
||||||
|
|
||||||
@@ -132,7 +135,6 @@ class allocator_multialloc_chain_node_deallocator
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
template<class ValueCompare, class Node>
|
template<class ValueCompare, class Node>
|
||||||
struct node_compare
|
struct node_compare
|
||||||
: private ValueCompare
|
: private ValueCompare
|
||||||
@@ -155,70 +157,90 @@ struct node_compare
|
|||||||
{ return ValueCompare::operator()(a.get_data(), b.get_data()); }
|
{ return ValueCompare::operator()(a.get_data(), b.get_data()); }
|
||||||
};
|
};
|
||||||
|
|
||||||
template<class A, class ICont>
|
template<class A, class ICont, class Pred = container_detail::nat>
|
||||||
struct node_alloc_holder
|
struct node_alloc_holder
|
||||||
{
|
{
|
||||||
typedef node_alloc_holder<A, ICont> self_t;
|
typedef allocator_traits<A> allocator_traits_type;
|
||||||
typedef typename A::value_type value_type;
|
typedef node_alloc_holder<A, ICont> self_t;
|
||||||
typedef typename ICont::value_type Node;
|
typedef typename allocator_traits_type::value_type value_type;
|
||||||
typedef typename A::template rebind<Node>::other NodeAlloc;
|
typedef typename ICont::value_type Node;
|
||||||
typedef A ValAlloc;
|
typedef typename allocator_traits_type::template
|
||||||
typedef typename NodeAlloc::pointer NodePtr;
|
portable_rebind_alloc<Node>::type NodeAlloc;
|
||||||
typedef containers_detail::scoped_deallocator<NodeAlloc> Deallocator;
|
typedef allocator_traits<NodeAlloc> node_allocator_traits_type;
|
||||||
typedef typename NodeAlloc::size_type size_type;
|
typedef A ValAlloc;
|
||||||
typedef typename NodeAlloc::difference_type difference_type;
|
typedef typename node_allocator_traits_type::pointer NodePtr;
|
||||||
typedef containers_detail::integral_constant<unsigned, 1> allocator_v1;
|
typedef container_detail::scoped_deallocator<NodeAlloc> Deallocator;
|
||||||
typedef containers_detail::integral_constant<unsigned, 2> allocator_v2;
|
typedef typename node_allocator_traits_type::size_type size_type;
|
||||||
typedef containers_detail::integral_constant<unsigned,
|
typedef typename node_allocator_traits_type::difference_type difference_type;
|
||||||
boost::container::containers_detail::
|
typedef container_detail::integral_constant<unsigned, 1> allocator_v1;
|
||||||
|
typedef container_detail::integral_constant<unsigned, 2> allocator_v2;
|
||||||
|
typedef container_detail::integral_constant<unsigned,
|
||||||
|
boost::container::container_detail::
|
||||||
version<NodeAlloc>::value> alloc_version;
|
version<NodeAlloc>::value> alloc_version;
|
||||||
typedef typename ICont::iterator icont_iterator;
|
typedef typename ICont::iterator icont_iterator;
|
||||||
typedef typename ICont::const_iterator icont_citerator;
|
typedef typename ICont::const_iterator icont_citerator;
|
||||||
typedef allocator_destroyer<NodeAlloc> Destroyer;
|
typedef allocator_destroyer<NodeAlloc> Destroyer;
|
||||||
|
typedef allocator_traits<NodeAlloc> NodeAllocTraits;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
BOOST_COPYABLE_AND_MOVABLE(node_alloc_holder)
|
BOOST_COPYABLE_AND_MOVABLE(node_alloc_holder)
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
node_alloc_holder(const ValAlloc &a)
|
//Constructors for sequence containers
|
||||||
|
node_alloc_holder()
|
||||||
|
: members_()
|
||||||
|
{}
|
||||||
|
|
||||||
|
explicit node_alloc_holder(const ValAlloc &a)
|
||||||
: members_(a)
|
: members_(a)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
node_alloc_holder(const node_alloc_holder &other)
|
explicit node_alloc_holder(const node_alloc_holder &x)
|
||||||
: members_(other.node_alloc())
|
: members_(NodeAllocTraits::select_on_container_copy_construction(x.node_alloc()))
|
||||||
{}
|
{}
|
||||||
|
|
||||||
node_alloc_holder(BOOST_RV_REF(node_alloc_holder) other)
|
explicit node_alloc_holder(BOOST_RV_REF(node_alloc_holder) x)
|
||||||
: members_(boost::move(other.node_alloc()))
|
: members_(boost::move(x.node_alloc()))
|
||||||
{ this->swap(other); }
|
{ this->icont().swap(x.icont()); }
|
||||||
|
|
||||||
node_alloc_holder & operator=(BOOST_COPY_ASSIGN_REF(node_alloc_holder) other)
|
//Constructors for associative containers
|
||||||
{ members_.assign(other.node_alloc()); }
|
explicit node_alloc_holder(const ValAlloc &a, const Pred &c)
|
||||||
|
: members_(a, c)
|
||||||
node_alloc_holder & operator=(BOOST_RV_REF(node_alloc_holder) other)
|
|
||||||
{ members_.assign(other.node_alloc()); }
|
|
||||||
|
|
||||||
template<class Pred>
|
|
||||||
node_alloc_holder(const ValAlloc &a, const Pred &c)
|
|
||||||
: members_(a, typename ICont::value_compare(c))
|
|
||||||
{}
|
{}
|
||||||
|
|
||||||
template<class Pred>
|
explicit node_alloc_holder(const node_alloc_holder &x, const Pred &c)
|
||||||
node_alloc_holder(BOOST_RV_REF(ValAlloc) a, const Pred &c)
|
: members_(NodeAllocTraits::select_on_container_copy_construction(x.node_alloc()), c)
|
||||||
: members_(a, typename ICont::value_compare(c))
|
|
||||||
{}
|
{}
|
||||||
|
|
||||||
template<class Pred>
|
explicit node_alloc_holder(const Pred &c)
|
||||||
node_alloc_holder(const node_alloc_holder &other, const Pred &c)
|
: members_(c)
|
||||||
: members_(other.node_alloc(), typename ICont::value_compare(c))
|
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
//helpers for move assignments
|
||||||
|
explicit node_alloc_holder(BOOST_RV_REF(node_alloc_holder) x, const Pred &c)
|
||||||
|
: members_(boost::move(x.node_alloc()), c)
|
||||||
|
{ this->icont().swap(x.icont()); }
|
||||||
|
|
||||||
|
void copy_assign_alloc(const node_alloc_holder &x)
|
||||||
|
{
|
||||||
|
container_detail::bool_<allocator_traits_type::propagate_on_container_copy_assignment::value> flag;
|
||||||
|
container_detail::assign_alloc( static_cast<NodeAlloc &>(this->members_)
|
||||||
|
, static_cast<const NodeAlloc &>(x.members_), flag);
|
||||||
|
}
|
||||||
|
|
||||||
|
void move_assign_alloc( node_alloc_holder &x)
|
||||||
|
{
|
||||||
|
container_detail::bool_<allocator_traits_type::propagate_on_container_move_assignment::value> flag;
|
||||||
|
container_detail::move_alloc( static_cast<NodeAlloc &>(this->members_)
|
||||||
|
, static_cast<NodeAlloc &>(x.members_), flag);
|
||||||
|
}
|
||||||
|
|
||||||
~node_alloc_holder()
|
~node_alloc_holder()
|
||||||
{ this->clear(alloc_version()); }
|
{ this->clear(alloc_version()); }
|
||||||
|
|
||||||
size_type max_size() const
|
size_type max_size() const
|
||||||
{ return this->node_alloc().max_size(); }
|
{ return allocator_traits_type::max_size(this->node_alloc()); }
|
||||||
|
|
||||||
NodePtr allocate_one()
|
NodePtr allocate_one()
|
||||||
{ return this->allocate_one(alloc_version()); }
|
{ return this->allocate_one(alloc_version()); }
|
||||||
@@ -229,131 +251,100 @@ struct node_alloc_holder
|
|||||||
NodePtr allocate_one(allocator_v2)
|
NodePtr allocate_one(allocator_v2)
|
||||||
{ return this->node_alloc().allocate_one(); }
|
{ return this->node_alloc().allocate_one(); }
|
||||||
|
|
||||||
void deallocate_one(NodePtr p)
|
void deallocate_one(const NodePtr &p)
|
||||||
{ return this->deallocate_one(p, alloc_version()); }
|
{ return this->deallocate_one(p, alloc_version()); }
|
||||||
|
|
||||||
void deallocate_one(NodePtr p, allocator_v1)
|
void deallocate_one(const NodePtr &p, allocator_v1)
|
||||||
{ this->node_alloc().deallocate(p, 1); }
|
{ this->node_alloc().deallocate(p, 1); }
|
||||||
|
|
||||||
void deallocate_one(NodePtr p, allocator_v2)
|
void deallocate_one(const NodePtr &p, allocator_v2)
|
||||||
{ this->node_alloc().deallocate_one(p); }
|
{ this->node_alloc().deallocate_one(p); }
|
||||||
|
/*
|
||||||
template<class Convertible1, class Convertible2>
|
template<class A, class Convertible1, class Convertible2>
|
||||||
static void construct(const NodePtr &ptr,
|
static void construct(A &a, const NodePtr &ptr,
|
||||||
BOOST_RV_REF_2_TEMPL_ARGS(std::pair, Convertible1, Convertible2) value)
|
BOOST_RV_REF_2_TEMPL_ARGS(std::pair, Convertible1, Convertible2) value)
|
||||||
{
|
{
|
||||||
typedef typename Node::hook_type hook_type;
|
typedef typename Node::hook_type hook_type;
|
||||||
typedef typename Node::value_type::first_type first_type;
|
typedef typename Node::value_type::first_type first_type;
|
||||||
typedef typename Node::value_type::second_type second_type;
|
typedef typename Node::value_type::second_type second_type;
|
||||||
Node *nodeptr = containers_detail::get_pointer(ptr);
|
Node *nodeptr = container_detail::to_raw_pointer(ptr);
|
||||||
|
|
||||||
//Hook constructor does not throw
|
//Hook constructor does not throw
|
||||||
new(static_cast<hook_type*>(nodeptr))hook_type();
|
allocator_traits<A>::construct(a, static_cast<hook_type*>(nodeptr));
|
||||||
|
|
||||||
//Now construct pair members_holder
|
//Now construct pair members_holder
|
||||||
value_type *valueptr = &nodeptr->get_data();
|
value_type *valueptr = &nodeptr->get_data();
|
||||||
new((void*)&valueptr->first) first_type(boost::move(value.first));
|
allocator_traits<A>::construct(a, &valueptr->first, boost::move(value.first));
|
||||||
BOOST_TRY{
|
BOOST_TRY{
|
||||||
new((void*)&valueptr->second) second_type(boost::move(value.second));
|
allocator_traits<A>::construct(a, &valueptr->second, boost::move(value.second));
|
||||||
}
|
}
|
||||||
BOOST_CATCH(...){
|
BOOST_CATCH(...){
|
||||||
valueptr->first.~first_type();
|
allocator_traits<A>::destroy(a, &valueptr->first);
|
||||||
static_cast<hook_type*>(nodeptr)->~hook_type();
|
|
||||||
BOOST_RETHROW
|
BOOST_RETHROW
|
||||||
}
|
}
|
||||||
BOOST_CATCH_END
|
BOOST_CATCH_END
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
static void destroy(const NodePtr &ptr)
|
#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
{ containers_detail::get_pointer(ptr)->~Node(); }
|
/*
|
||||||
|
template<class A, class ...Args>
|
||||||
Deallocator create_node_and_deallocator()
|
static void construct(A &a, const NodePtr &ptr, Args &&...args)
|
||||||
{
|
{
|
||||||
return Deallocator(this->allocate_one(), this->node_alloc());
|
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
|
||||||
|
|
||||||
template<class ...Args>
|
|
||||||
static void construct(const NodePtr &ptr, Args &&...args)
|
|
||||||
{ new((void*)containers_detail::get_pointer(ptr)) Node(boost::forward<Args>(args)...); }
|
|
||||||
|
|
||||||
template<class ...Args>
|
template<class ...Args>
|
||||||
NodePtr create_node(Args &&...args)
|
NodePtr create_node(Args &&...args)
|
||||||
{
|
{
|
||||||
NodePtr p = this->allocate_one();
|
NodePtr p = this->allocate_one();
|
||||||
Deallocator node_deallocator(p, this->node_alloc());
|
Deallocator node_deallocator(p, this->node_alloc());
|
||||||
self_t::construct(p, boost::forward<Args>(args)...);
|
allocator_traits<NodeAlloc>::construct
|
||||||
|
(this->node_alloc(), container_detail::to_raw_pointer(p), boost::forward<Args>(args)...);
|
||||||
node_deallocator.release();
|
node_deallocator.release();
|
||||||
return (p);
|
return (p);
|
||||||
}
|
}
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
static void construct(const NodePtr &ptr)
|
|
||||||
{ new((void*)containers_detail::get_pointer(ptr)) Node(); }
|
|
||||||
|
|
||||||
NodePtr create_node()
|
|
||||||
{
|
|
||||||
NodePtr p = this->allocate_one();
|
|
||||||
Deallocator node_deallocator(p, this->node_alloc());
|
|
||||||
self_t::construct(p);
|
|
||||||
node_deallocator.release();
|
|
||||||
return (p);
|
|
||||||
}
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
void construct(const NodePtr &ptr, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
{ \
|
|
||||||
new((void*)containers_detail::get_pointer(ptr)) \
|
|
||||||
Node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
|
||||||
} \
|
|
||||||
//!
|
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
\
|
||||||
NodePtr create_node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
NodePtr create_node(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
NodePtr p = this->allocate_one(); \
|
NodePtr p = this->allocate_one(); \
|
||||||
Deallocator node_deallocator(p, this->node_alloc()); \
|
Deallocator node_deallocator(p, this->node_alloc()); \
|
||||||
self_t::construct(p, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
allocator_traits<NodeAlloc>::construct \
|
||||||
|
(this->node_alloc(), container_detail::to_raw_pointer(p) \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); \
|
||||||
node_deallocator.release(); \
|
node_deallocator.release(); \
|
||||||
return (p); \
|
return (p); \
|
||||||
} \
|
} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
template<class It>
|
template<class It>
|
||||||
NodePtr create_node_from_it(It it)
|
NodePtr create_node_from_it(const It &it)
|
||||||
{
|
{
|
||||||
NodePtr p = this->allocate_one();
|
NodePtr p = this->allocate_one();
|
||||||
Deallocator node_deallocator(p, this->node_alloc());
|
Deallocator node_deallocator(p, this->node_alloc());
|
||||||
::boost::container::construct_in_place(containers_detail::get_pointer(p), it);
|
::boost::container::construct_in_place(this->node_alloc(), container_detail::to_raw_pointer(p), it);
|
||||||
node_deallocator.release();
|
node_deallocator.release();
|
||||||
return (p);
|
return (p);
|
||||||
}
|
}
|
||||||
|
|
||||||
void destroy_node(NodePtr node)
|
void destroy_node(const NodePtr &nodep)
|
||||||
{
|
{
|
||||||
self_t::destroy(node);
|
allocator_traits<NodeAlloc>::destroy(this->node_alloc(), container_detail::to_raw_pointer(nodep));
|
||||||
this->deallocate_one(node);
|
this->deallocate_one(nodep);
|
||||||
}
|
}
|
||||||
|
|
||||||
void swap(node_alloc_holder &x)
|
void swap(node_alloc_holder &x)
|
||||||
{
|
{
|
||||||
NodeAlloc& this_alloc = this->node_alloc();
|
|
||||||
NodeAlloc& other_alloc = x.node_alloc();
|
|
||||||
|
|
||||||
if (this_alloc != other_alloc){
|
|
||||||
containers_detail::do_swap(this_alloc, other_alloc);
|
|
||||||
}
|
|
||||||
|
|
||||||
this->icont().swap(x.icont());
|
this->icont().swap(x.icont());
|
||||||
|
container_detail::bool_<allocator_traits_type::propagate_on_container_swap::value> flag;
|
||||||
|
container_detail::swap_alloc(this->node_alloc(), x.node_alloc(), flag);
|
||||||
}
|
}
|
||||||
|
|
||||||
template<class FwdIterator, class Inserter>
|
template<class FwdIterator, class Inserter>
|
||||||
@@ -369,11 +360,11 @@ struct node_alloc_holder
|
|||||||
Node *p = 0;
|
Node *p = 0;
|
||||||
BOOST_TRY{
|
BOOST_TRY{
|
||||||
for(difference_type i = 0; i < n; ++i, ++beg, --constructed){
|
for(difference_type i = 0; i < n; ++i, ++beg, --constructed){
|
||||||
p = containers_detail::get_pointer(mem.front());
|
p = container_detail::to_raw_pointer(mem.front());
|
||||||
mem.pop_front();
|
mem.pop_front();
|
||||||
//This can throw
|
//This can throw
|
||||||
constructed = 0;
|
constructed = 0;
|
||||||
boost::container::construct_in_place(p, beg);
|
boost::container::construct_in_place(this->node_alloc(), p, beg);
|
||||||
++constructed;
|
++constructed;
|
||||||
//This can throw in some containers (predicate might throw)
|
//This can throw in some containers (predicate might throw)
|
||||||
inserter(*p);
|
inserter(*p);
|
||||||
@@ -381,7 +372,7 @@ struct node_alloc_holder
|
|||||||
}
|
}
|
||||||
BOOST_CATCH(...){
|
BOOST_CATCH(...){
|
||||||
if(constructed){
|
if(constructed){
|
||||||
this->destroy(p);
|
allocator_traits<NodeAlloc>::destroy(this->node_alloc(), container_detail::to_raw_pointer(p));
|
||||||
}
|
}
|
||||||
this->node_alloc().deallocate_individual(boost::move(mem));
|
this->node_alloc().deallocate_individual(boost::move(mem));
|
||||||
BOOST_RETHROW
|
BOOST_RETHROW
|
||||||
@@ -404,10 +395,10 @@ struct node_alloc_holder
|
|||||||
this->node_alloc().deallocate_individual(boost::move(chain));
|
this->node_alloc().deallocate_individual(boost::move(chain));
|
||||||
}
|
}
|
||||||
|
|
||||||
icont_iterator erase_range(icont_iterator first, icont_iterator last, allocator_v1)
|
icont_iterator erase_range(const icont_iterator &first, const icont_iterator &last, allocator_v1)
|
||||||
{ return this->icont().erase_and_dispose(first, last, Destroyer(this->node_alloc())); }
|
{ return this->icont().erase_and_dispose(first, last, Destroyer(this->node_alloc())); }
|
||||||
|
|
||||||
icont_iterator erase_range(icont_iterator first, icont_iterator last, allocator_v2)
|
icont_iterator erase_range(const icont_iterator &first, const icont_iterator &last, allocator_v2)
|
||||||
{
|
{
|
||||||
allocator_multialloc_chain_node_deallocator<NodeAlloc> chain_holder(this->node_alloc());
|
allocator_multialloc_chain_node_deallocator<NodeAlloc> chain_holder(this->node_alloc());
|
||||||
return this->icont().erase_and_dispose(first, last, chain_holder.get_chain_builder());
|
return this->icont().erase_and_dispose(first, last, chain_holder.get_chain_builder());
|
||||||
@@ -437,44 +428,38 @@ struct node_alloc_holder
|
|||||||
node_alloc_holder &m_holder;
|
node_alloc_holder &m_holder;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct destroyer
|
|
||||||
{
|
|
||||||
destroyer(node_alloc_holder &holder)
|
|
||||||
: m_holder(holder)
|
|
||||||
{}
|
|
||||||
|
|
||||||
void operator()(NodePtr n) const
|
|
||||||
{ m_holder.destroy_node(n); }
|
|
||||||
|
|
||||||
node_alloc_holder &m_holder;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct members_holder
|
struct members_holder
|
||||||
: public NodeAlloc
|
: public NodeAlloc
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
members_holder(const members_holder&);
|
members_holder(const members_holder&);
|
||||||
|
members_holder & operator=(const members_holder&);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
template<class ConvertibleToAlloc>
|
members_holder()
|
||||||
members_holder(const ConvertibleToAlloc &c2alloc)
|
: NodeAlloc(), m_icont()
|
||||||
: NodeAlloc(c2alloc)
|
|
||||||
{}
|
|
||||||
|
|
||||||
template<class ConvertibleToAlloc, class Pred>
|
|
||||||
members_holder(const ConvertibleToAlloc &c2alloc, const Pred &c)
|
|
||||||
: NodeAlloc(c2alloc), m_icont(c)
|
|
||||||
{}
|
{}
|
||||||
|
|
||||||
template<class ConvertibleToAlloc>
|
template<class ConvertibleToAlloc>
|
||||||
void assign (const ConvertibleToAlloc &c2alloc)
|
explicit members_holder(BOOST_FWD_REF(ConvertibleToAlloc) c2alloc)
|
||||||
{
|
: NodeAlloc(boost::forward<ConvertibleToAlloc>(c2alloc))
|
||||||
NodeAlloc::operator=(c2alloc);
|
, m_icont()
|
||||||
}
|
{}
|
||||||
|
|
||||||
|
template<class ConvertibleToAlloc>
|
||||||
|
members_holder(BOOST_FWD_REF(ConvertibleToAlloc) c2alloc, const Pred &c)
|
||||||
|
: NodeAlloc(boost::forward<ConvertibleToAlloc>(c2alloc))
|
||||||
|
, m_icont(typename ICont::value_compare(c))
|
||||||
|
{}
|
||||||
|
|
||||||
|
explicit members_holder(const Pred &c)
|
||||||
|
: NodeAlloc()
|
||||||
|
, m_icont(typename ICont::value_compare(c))
|
||||||
|
{}
|
||||||
|
|
||||||
//The intrusive container
|
//The intrusive container
|
||||||
ICont m_icont;
|
ICont m_icont;
|
||||||
} members_;
|
};
|
||||||
|
|
||||||
ICont &non_const_icont() const
|
ICont &non_const_icont() const
|
||||||
{ return const_cast<ICont&>(this->members_.m_icont); }
|
{ return const_cast<ICont&>(this->members_.m_icont); }
|
||||||
@@ -490,12 +475,14 @@ struct node_alloc_holder
|
|||||||
|
|
||||||
const NodeAlloc &node_alloc() const
|
const NodeAlloc &node_alloc() const
|
||||||
{ return static_cast<const NodeAlloc &>(this->members_); }
|
{ return static_cast<const NodeAlloc &>(this->members_); }
|
||||||
|
|
||||||
|
members_holder members_;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif // BOOST_CONTAINERS_DETAIL_NODE_ALLOC_HPP_
|
#endif // BOOST_CONTAINER_DETAIL_NODE_ALLOC_HPP_
|
||||||
|
@@ -19,7 +19,7 @@
|
|||||||
#include <boost/container/container_fwd.hpp>
|
#include <boost/container/container_fwd.hpp>
|
||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
#include <boost/container/detail/utilities.hpp>
|
#include <boost/container/detail/utilities.hpp>
|
||||||
#include <boost/pointer_to_other.hpp>
|
#include <boost/intrusive/pointer_traits.hpp>
|
||||||
#include <boost/intrusive/set.hpp>
|
#include <boost/intrusive/set.hpp>
|
||||||
#include <boost/intrusive/slist.hpp>
|
#include <boost/intrusive/slist.hpp>
|
||||||
#include <boost/container/detail/type_traits.hpp>
|
#include <boost/container/detail/type_traits.hpp>
|
||||||
@@ -32,7 +32,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class SegmentManagerBase>
|
template<class SegmentManagerBase>
|
||||||
class private_node_pool_impl
|
class private_node_pool_impl
|
||||||
@@ -82,7 +82,7 @@ class private_node_pool_impl
|
|||||||
|
|
||||||
//!Returns the segment manager. Never throws
|
//!Returns the segment manager. Never throws
|
||||||
segment_manager_base_type* get_segment_manager_base()const
|
segment_manager_base_type* get_segment_manager_base()const
|
||||||
{ return containers_detail::get_pointer(mp_segment_mngr_base); }
|
{ return container_detail::to_raw_pointer(mp_segment_mngr_base); }
|
||||||
|
|
||||||
void *allocate_node()
|
void *allocate_node()
|
||||||
{ return priv_alloc_node(); }
|
{ return priv_alloc_node(); }
|
||||||
@@ -346,8 +346,8 @@ class private_node_pool_impl
|
|||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef typename boost::pointer_to_other
|
typedef typename boost::intrusive::pointer_traits
|
||||||
<void_pointer, segment_manager_base_type>::type segment_mngr_base_ptr_t;
|
<void_pointer>::template rebind_pointer<segment_manager_base_type>::type segment_mngr_base_ptr_t;
|
||||||
|
|
||||||
const size_type m_nodes_per_block;
|
const size_type m_nodes_per_block;
|
||||||
const size_type m_real_node_size;
|
const size_type m_real_node_size;
|
||||||
@@ -358,7 +358,7 @@ class private_node_pool_impl
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
|
@@ -10,8 +10,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_CONTAINERS_DETAIL_PAIR_HPP
|
#ifndef BOOST_CONTAINER_CONTAINER_DETAIL_PAIR_HPP
|
||||||
#define BOOST_CONTAINERS_CONTAINERS_DETAIL_PAIR_HPP
|
#define BOOST_CONTAINER_CONTAINER_DETAIL_PAIR_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -28,13 +28,13 @@
|
|||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
#include <boost/type_traits/is_class.hpp>
|
#include <boost/type_traits/is_class.hpp>
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
#include <boost/container/detail/preprocessor.hpp>
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template <class T1, class T2>
|
template <class T1, class T2>
|
||||||
struct pair;
|
struct pair;
|
||||||
@@ -143,13 +143,13 @@ struct pair
|
|||||||
/*
|
/*
|
||||||
//Variadic versions
|
//Variadic versions
|
||||||
template<class U>
|
template<class U>
|
||||||
pair(BOOST_CONTAINERS_PARAM(U, u), typename containers_detail::disable_if
|
pair(BOOST_CONTAINER_PP_PARAM(U, u), typename container_detail::disable_if
|
||||||
< containers_detail::is_pair< typename containers_detail::remove_ref_const<U>::type >, pair_nat>::type* = 0)
|
< container_detail::is_pair< typename container_detail::remove_ref_const<U>::type >, pair_nat>::type* = 0)
|
||||||
: first(::boost::forward<U>(u))
|
: first(::boost::forward<U>(u))
|
||||||
, second()
|
, second()
|
||||||
{}
|
{}
|
||||||
|
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
template<class U, class V, class ...Args>
|
template<class U, class V, class ...Args>
|
||||||
pair(U &&u, V &&v)
|
pair(U &&u, V &&v)
|
||||||
@@ -161,13 +161,13 @@ struct pair
|
|||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<class U, BOOST_PP_ENUM_PARAMS(n, class P)> \
|
template<class U, BOOST_PP_ENUM_PARAMS(n, class P)> \
|
||||||
pair(BOOST_CONTAINERS_PARAM(U, u) \
|
pair(BOOST_CONTAINER_PP_PARAM(U, u) \
|
||||||
,BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
,BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
: first(::boost::forward<U>(u)) \
|
: first(::boost::forward<U>(u)) \
|
||||||
, second(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)) \
|
, second(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)) \
|
||||||
{} \
|
{} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
#endif
|
#endif
|
||||||
*/
|
*/
|
||||||
@@ -280,7 +280,7 @@ inline void swap(pair<T1, T2>& x, pair<T1, T2>& y)
|
|||||||
swap(x.second, y.second);
|
swap(x.second, y.second);
|
||||||
}
|
}
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
|
|
||||||
|
|
||||||
@@ -291,7 +291,7 @@ template<class T>
|
|||||||
struct is_enum;
|
struct is_enum;
|
||||||
|
|
||||||
template<class T, class U>
|
template<class T, class U>
|
||||||
struct is_enum< ::boost::container::containers_detail::pair<T, U> >
|
struct is_enum< ::boost::container::container_detail::pair<T, U> >
|
||||||
{
|
{
|
||||||
static const bool value = false;
|
static const bool value = false;
|
||||||
};
|
};
|
||||||
@@ -299,14 +299,14 @@ struct is_enum< ::boost::container::containers_detail::pair<T, U> >
|
|||||||
//This specialization is needed to avoid instantiation of pair in
|
//This specialization is needed to avoid instantiation of pair in
|
||||||
//is_class, and allow recursive maps.
|
//is_class, and allow recursive maps.
|
||||||
template <class T1, class T2>
|
template <class T1, class T2>
|
||||||
struct is_class< ::boost::container::containers_detail::pair<T1, T2> >
|
struct is_class< ::boost::container::container_detail::pair<T1, T2> >
|
||||||
: public ::boost::true_type
|
: public ::boost::true_type
|
||||||
{};
|
{};
|
||||||
|
|
||||||
#ifdef BOOST_NO_RVALUE_REFERENCES
|
#ifdef BOOST_NO_RVALUE_REFERENCES
|
||||||
|
|
||||||
template<class T1, class T2>
|
template<class T1, class T2>
|
||||||
struct has_move_emulation_enabled< ::boost::container::containers_detail::pair<T1, T2> >
|
struct has_move_emulation_enabled< ::boost::container::container_detail::pair<T1, T2> >
|
||||||
: ::boost::true_type
|
: ::boost::true_type
|
||||||
{};
|
{};
|
||||||
|
|
||||||
@@ -317,4 +317,4 @@ struct has_move_emulation_enabled< ::boost::container::containers_detail::pair<T
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_PAIR_HPP
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_PAIR_HPP
|
||||||
|
@@ -21,7 +21,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class VoidPointer>
|
template<class VoidPointer>
|
||||||
struct node_slist
|
struct node_slist
|
||||||
@@ -43,7 +43,7 @@ struct is_stateless_segment_manager
|
|||||||
static const bool value = false;
|
static const bool value = false;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
|
@@ -8,32 +8,43 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_PREPROCESSOR_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_PREPROCESSOR_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_PREPROCESSOR_HPP
|
#define BOOST_CONTAINER_DETAIL_PREPROCESSOR_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include "config_begin.hpp"
|
#include <boost/container/detail/config_begin.hpp>
|
||||||
|
|
||||||
#ifndef BOOST_NO_RVALUE_REFERENCES
|
#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
#include <boost/container/detail/stored_ref.hpp>
|
#include <boost/container/detail/stored_ref.hpp>
|
||||||
#endif
|
#endif //#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
|
|
||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
|
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
#error "This file is not needed when perfect forwarding is available"
|
//#error "This file is not needed when perfect forwarding is available"
|
||||||
#endif
|
#endif //BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
#include <boost/preprocessor/iteration/local.hpp>
|
#include <boost/preprocessor/iteration/local.hpp>
|
||||||
#include <boost/preprocessor/repetition/enum_params.hpp>
|
#include <boost/preprocessor/punctuation/paren_if.hpp>
|
||||||
|
#include <boost/preprocessor/punctuation/comma_if.hpp>
|
||||||
|
#include <boost/preprocessor/control/expr_if.hpp>
|
||||||
#include <boost/preprocessor/cat.hpp>
|
#include <boost/preprocessor/cat.hpp>
|
||||||
#include <boost/preprocessor/repetition/enum.hpp>
|
#include <boost/preprocessor/repetition/enum.hpp>
|
||||||
|
#include <boost/preprocessor/repetition/enum_params.hpp>
|
||||||
|
#include <boost/preprocessor/repetition/enum_trailing_params.hpp>
|
||||||
|
#include <boost/preprocessor/repetition/enum_trailing.hpp>
|
||||||
|
#include <boost/preprocessor/repetition/enum_shifted_params.hpp>
|
||||||
|
#include <boost/preprocessor/repetition/enum_shifted.hpp>
|
||||||
#include <boost/preprocessor/repetition/repeat.hpp>
|
#include <boost/preprocessor/repetition/repeat.hpp>
|
||||||
|
#include <boost/preprocessor/logical/not.hpp>
|
||||||
|
#include <boost/preprocessor/arithmetic/sub.hpp>
|
||||||
|
#include <boost/preprocessor/arithmetic/add.hpp>
|
||||||
|
#include <boost/preprocessor/iteration/iterate.hpp>
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS 10
|
#define BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS 10
|
||||||
|
|
||||||
//Note:
|
//Note:
|
||||||
//We define template parameters as const references to
|
//We define template parameters as const references to
|
||||||
@@ -42,100 +53,126 @@
|
|||||||
//is achieved in C++0x. Meanwhile, if we want to be able to
|
//is achieved in C++0x. Meanwhile, if we want to be able to
|
||||||
//bind rvalues with non-const references, we have to be ugly
|
//bind rvalues with non-const references, we have to be ugly
|
||||||
#ifndef BOOST_NO_RVALUE_REFERENCES
|
#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
#define BOOST_CONTAINERS_PP_PARAM_LIST(z, n, data) \
|
#define BOOST_CONTAINER_PP_PARAM_LIST(z, n, data) \
|
||||||
BOOST_PP_CAT(P, n) && BOOST_PP_CAT(p, n) \
|
BOOST_PP_CAT(P, n) && BOOST_PP_CAT(p, n) \
|
||||||
//!
|
//!
|
||||||
#else
|
#else
|
||||||
#define BOOST_CONTAINERS_PP_PARAM_LIST(z, n, data) \
|
#define BOOST_CONTAINER_PP_PARAM_LIST(z, n, data) \
|
||||||
const BOOST_PP_CAT(P, n) & BOOST_PP_CAT(p, n) \
|
const BOOST_PP_CAT(P, n) & BOOST_PP_CAT(p, n) \
|
||||||
//!
|
//!
|
||||||
#endif
|
#endif //#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
|
|
||||||
#ifndef BOOST_NO_RVALUE_REFERENCES
|
#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
#define BOOST_CONTAINERS_PARAM(U, u) \
|
#define BOOST_CONTAINER_PP_PARAM(U, u) \
|
||||||
U && u \
|
U && u \
|
||||||
//!
|
//!
|
||||||
#else
|
#else
|
||||||
#define BOOST_CONTAINERS_PARAM(U, u) \
|
#define BOOST_CONTAINER_PP_PARAM(U, u) \
|
||||||
const U & u \
|
const U & u \
|
||||||
//!
|
//!
|
||||||
#endif
|
#endif //#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
|
|
||||||
#ifndef BOOST_NO_RVALUE_REFERENCES
|
#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
|
|
||||||
#ifdef BOOST_MOVE_OLD_RVALUE_REF_BINDING_RULES
|
#ifdef BOOST_MOVE_OLD_RVALUE_REF_BINDING_RULES
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_AUX_PARAM_INIT(z, n, data) \
|
#define BOOST_CONTAINER_PP_PARAM_INIT(z, n, data) \
|
||||||
BOOST_PP_CAT(m_p, n) (boost::forward< BOOST_PP_CAT(P, n) >( BOOST_PP_CAT(p, n) )) \
|
BOOST_PP_CAT(m_p, n) (boost::forward< BOOST_PP_CAT(P, n) >( BOOST_PP_CAT(p, n) )) \
|
||||||
//!
|
//!
|
||||||
|
|
||||||
#else
|
#else //BOOST_MOVE_OLD_RVALUE_REF_BINDING_RULES
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_AUX_PARAM_INIT(z, n, data) \
|
#define BOOST_CONTAINER_PP_PARAM_INIT(z, n, data) \
|
||||||
BOOST_PP_CAT(m_p, n) (static_cast<BOOST_PP_CAT(P, n)>( BOOST_PP_CAT(p, n) )) \
|
BOOST_PP_CAT(m_p, n) (static_cast<BOOST_PP_CAT(P, n)>( BOOST_PP_CAT(p, n) )) \
|
||||||
//!
|
//!
|
||||||
|
|
||||||
#endif
|
#endif //BOOST_MOVE_OLD_RVALUE_REF_BINDING_RULES
|
||||||
|
|
||||||
#else
|
#else //BOOST_NO_RVALUE_REFERENCES
|
||||||
#define BOOST_CONTAINERS_AUX_PARAM_INIT(z, n, data) \
|
|
||||||
BOOST_PP_CAT(m_p, n) (const_cast<BOOST_PP_CAT(P, n) &>(BOOST_PP_CAT(p, n))) \
|
|
||||||
//!
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_AUX_PARAM_INC(z, n, data) \
|
#define BOOST_CONTAINER_PP_PARAM_INIT(z, n, data) \
|
||||||
BOOST_PP_CAT(++m_p, n) \
|
BOOST_PP_CAT(m_p, n) (const_cast<BOOST_PP_CAT(P, n) &>(BOOST_PP_CAT(p, n))) \
|
||||||
//!
|
//!
|
||||||
|
#endif //#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
|
|
||||||
#ifndef BOOST_NO_RVALUE_REFERENCES
|
#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
|
|
||||||
#if defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
#if defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_AUX_PARAM_DEFINE(z, n, data) \
|
#define BOOST_CONTAINER_PP_PARAM_DEFINE(z, n, data) \
|
||||||
BOOST_PP_CAT(P, n) & BOOST_PP_CAT(m_p, n); \
|
BOOST_PP_CAT(P, n) & BOOST_PP_CAT(m_p, n); \
|
||||||
//!
|
//!
|
||||||
|
|
||||||
#else
|
#else //BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_AUX_PARAM_DEFINE(z, n, data) \
|
#define BOOST_CONTAINER_PP_PARAM_DEFINE(z, n, data) \
|
||||||
BOOST_PP_CAT(P, n) && BOOST_PP_CAT(m_p, n); \
|
BOOST_PP_CAT(P, n) && BOOST_PP_CAT(m_p, n); \
|
||||||
//!
|
//!
|
||||||
|
|
||||||
#endif //defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
#endif //defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
||||||
|
|
||||||
|
#else //BOOST_NO_RVALUE_REFERENCES
|
||||||
|
|
||||||
#else
|
#define BOOST_CONTAINER_PP_PARAM_DEFINE(z, n, data) \
|
||||||
#define BOOST_CONTAINERS_AUX_PARAM_DEFINE(z, n, data) \
|
BOOST_PP_CAT(P, n) & BOOST_PP_CAT(m_p, n); \
|
||||||
BOOST_PP_CAT(P, n) & BOOST_PP_CAT(m_p, n); \
|
//!
|
||||||
//!
|
#endif //#ifndef BOOST_NO_RVALUE_REFERENCES
|
||||||
#endif
|
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_PP_PARAM_FORWARD(z, n, data) \
|
|
||||||
boost::forward< BOOST_PP_CAT(P, n) >( BOOST_PP_CAT(p, n) ) \
|
|
||||||
//!
|
|
||||||
|
|
||||||
#if !defined(BOOST_NO_RVALUE_REFERENCES) && defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
#if !defined(BOOST_NO_RVALUE_REFERENCES) && defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_PP_MEMBER_FORWARD(z, n, data) \
|
#define BOOST_CONTAINER_PP_MEMBER_FORWARD(z, n, data) \
|
||||||
::boost::container::containers_detail::stored_ref< BOOST_PP_CAT(P, n) >::forward( BOOST_PP_CAT(m_p, n) ) \
|
::boost::container::container_detail::stored_ref< BOOST_PP_CAT(P, n) >::forward( BOOST_PP_CAT(this->m_p, n) ) \
|
||||||
//!
|
//!
|
||||||
|
|
||||||
#else
|
#else //!defined(BOOST_NO_RVALUE_REFERENCES) && defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_PP_MEMBER_FORWARD(z, n, data) \
|
#define BOOST_CONTAINER_PP_MEMBER_FORWARD(z, n, data) \
|
||||||
boost::forward< BOOST_PP_CAT(P, n) >( BOOST_PP_CAT(m_p, n) ) \
|
boost::forward< BOOST_PP_CAT(P, n) >( BOOST_PP_CAT(this->m_p, n) ) \
|
||||||
//!
|
//!
|
||||||
|
|
||||||
#endif //!defined(BOOST_NO_RVALUE_REFERENCES) && defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
#endif //!defined(BOOST_NO_RVALUE_REFERENCES) && defined(BOOST_MOVE_MSVC_10_MEMBER_RVALUE_REF_BUG)
|
||||||
|
|
||||||
#define BOOST_CONTAINERS_PP_MEMBER_IT_FORWARD(z, n, data) \
|
#define BOOST_CONTAINER_PP_PARAM_INC(z, n, data) \
|
||||||
BOOST_PP_CAT(*m_p, n) \
|
BOOST_PP_CAT(++this->m_p, n) \
|
||||||
|
//!
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_PP_IDENTITY(z, n, data) data
|
||||||
|
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_PP_PARAM_FORWARD(z, n, data) \
|
||||||
|
boost::forward< BOOST_PP_CAT(P, n) >( BOOST_PP_CAT(p, n) ) \
|
||||||
|
//!
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_PP_DECLVAL(z, n, data) \
|
||||||
|
boost::move_detail::declval< BOOST_PP_CAT(P, n) >() \
|
||||||
|
//!
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_PP_MEMBER_IT_FORWARD(z, n, data) \
|
||||||
|
BOOST_PP_CAT(*this->m_p, n) \
|
||||||
|
//!
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_PP_TEMPLATE_PARAM_VOID_DEFAULT(z, n, data) \
|
||||||
|
BOOST_PP_CAT(class P, n) = void \
|
||||||
|
//!
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_PP_STATIC_PARAM_REF_DECLARE(z, n, data) \
|
||||||
|
static BOOST_PP_CAT(P, n) & BOOST_PP_CAT(p, n); \
|
||||||
|
//!
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_PP_PARAM_PASS(z, n, data) \
|
||||||
|
BOOST_PP_CAT(p, n) \
|
||||||
|
//!
|
||||||
|
|
||||||
|
#define BOOST_CONTAINER_PP_FWD_TYPE(z, n, data) \
|
||||||
|
typename ::boost::move_detail::forward_type< BOOST_PP_CAT(P, n) >::type \
|
||||||
//!
|
//!
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#else
|
//#else
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
|
||||||
#error "This file is not needed when perfect forwarding is available"
|
//#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
#endif
|
//#error "This file is not needed when perfect forwarding is available"
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_PREPROCESSOR_HPP
|
//#endif //BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_PREPROCESSOR_HPP
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_STORED_REF_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_STORED_REF_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_STORED_REF_HPP
|
#define BOOST_CONTAINER_DETAIL_STORED_REF_HPP
|
||||||
|
|
||||||
#include "config_begin.hpp"
|
#include "config_begin.hpp"
|
||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
@@ -18,7 +18,7 @@
|
|||||||
|
|
||||||
namespace boost{
|
namespace boost{
|
||||||
namespace container{
|
namespace container{
|
||||||
namespace containers_detail{
|
namespace container_detail{
|
||||||
|
|
||||||
template<class T>
|
template<class T>
|
||||||
struct stored_ref
|
struct stored_ref
|
||||||
@@ -79,7 +79,7 @@ struct stored_ref<T&>
|
|||||||
{ return t; }
|
{ return t; }
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail{
|
} //namespace container_detail{
|
||||||
} //namespace container{
|
} //namespace container{
|
||||||
} //namespace boost{
|
} //namespace boost{
|
||||||
|
|
||||||
@@ -89,4 +89,4 @@ struct stored_ref<T&>
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //BOOST_CONTAINERS_DETAIL_STORED_REF_HPP
|
#endif //BOOST_CONTAINER_DETAIL_STORED_REF_HPP
|
||||||
|
@@ -11,8 +11,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_TRANSFORM_ITERATORS_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_TRANSFORM_ITERATORS_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_TRANSFORM_ITERATORS_HPP
|
#define BOOST_CONTAINER_DETAIL_TRANSFORM_ITERATORS_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -59,7 +59,7 @@ class transform_iterator
|
|||||||
: public UnaryFunction
|
: public UnaryFunction
|
||||||
, public std::iterator
|
, public std::iterator
|
||||||
< typename Iterator::iterator_category
|
< typename Iterator::iterator_category
|
||||||
, typename containers_detail::remove_reference<typename UnaryFunction::result_type>::type
|
, typename container_detail::remove_reference<typename UnaryFunction::result_type>::type
|
||||||
, typename Iterator::difference_type
|
, typename Iterator::difference_type
|
||||||
, operator_arrow_proxy<typename UnaryFunction::result_type>
|
, operator_arrow_proxy<typename UnaryFunction::result_type>
|
||||||
, typename UnaryFunction::result_type>
|
, typename UnaryFunction::result_type>
|
||||||
@@ -173,4 +173,4 @@ make_transform_iterator(Iterator it, UnaryFunc fun)
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_TRANSFORM_ITERATORS_HPP
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_TRANSFORM_ITERATORS_HPP
|
||||||
|
@@ -8,15 +8,15 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_TREE_HPP
|
#ifndef BOOST_CONTAINER_TREE_HPP
|
||||||
#define BOOST_CONTAINERS_TREE_HPP
|
#define BOOST_CONTAINER_TREE_HPP
|
||||||
|
|
||||||
#include "config_begin.hpp"
|
#include "config_begin.hpp"
|
||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
#include <boost/container/container_fwd.hpp>
|
#include <boost/container/container_fwd.hpp>
|
||||||
|
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
#include <boost/pointer_to_other.hpp>
|
#include <boost/intrusive/pointer_traits.hpp>
|
||||||
#include <boost/type_traits/has_trivial_destructor.hpp>
|
#include <boost/type_traits/has_trivial_destructor.hpp>
|
||||||
#include <boost/detail/no_exceptions_support.hpp>
|
#include <boost/detail/no_exceptions_support.hpp>
|
||||||
#include <boost/intrusive/rbtree.hpp>
|
#include <boost/intrusive/rbtree.hpp>
|
||||||
@@ -27,7 +27,8 @@
|
|||||||
#include <boost/container/detail/destroyers.hpp>
|
#include <boost/container/detail/destroyers.hpp>
|
||||||
#include <boost/container/detail/pair.hpp>
|
#include <boost/container/detail/pair.hpp>
|
||||||
#include <boost/container/detail/type_traits.hpp>
|
#include <boost/container/detail/type_traits.hpp>
|
||||||
#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
|
#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
#include <boost/container/detail/preprocessor.hpp>
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -37,7 +38,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class Key, class Value, class KeyCompare, class KeyOfValue>
|
template<class Key, class Value, class KeyCompare, class KeyOfValue>
|
||||||
struct value_compare_impl
|
struct value_compare_impl
|
||||||
@@ -82,10 +83,10 @@ struct value_compare_impl
|
|||||||
template<class VoidPointer>
|
template<class VoidPointer>
|
||||||
struct rbtree_hook
|
struct rbtree_hook
|
||||||
{
|
{
|
||||||
typedef typename containers_detail::bi::make_set_base_hook
|
typedef typename container_detail::bi::make_set_base_hook
|
||||||
< containers_detail::bi::void_pointer<VoidPointer>
|
< container_detail::bi::void_pointer<VoidPointer>
|
||||||
, containers_detail::bi::link_mode<containers_detail::bi::normal_link>
|
, container_detail::bi::link_mode<container_detail::bi::normal_link>
|
||||||
, containers_detail::bi::optimize_size<true>
|
, container_detail::bi::optimize_size<true>
|
||||||
>::type type;
|
>::type type;
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -105,6 +106,10 @@ template <class T, class VoidPointer>
|
|||||||
struct rbtree_node
|
struct rbtree_node
|
||||||
: public rbtree_hook<VoidPointer>::type
|
: public rbtree_hook<VoidPointer>::type
|
||||||
{
|
{
|
||||||
|
private:
|
||||||
|
BOOST_COPYABLE_AND_MOVABLE(rbtree_node)
|
||||||
|
|
||||||
|
public:
|
||||||
typedef typename rbtree_hook<VoidPointer>::type hook_type;
|
typedef typename rbtree_hook<VoidPointer>::type hook_type;
|
||||||
|
|
||||||
typedef T value_type;
|
typedef T value_type;
|
||||||
@@ -112,8 +117,6 @@ struct rbtree_node
|
|||||||
|
|
||||||
typedef rbtree_node<T, VoidPointer> node_type;
|
typedef rbtree_node<T, VoidPointer> node_type;
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
|
||||||
|
|
||||||
rbtree_node()
|
rbtree_node()
|
||||||
: m_data()
|
: m_data()
|
||||||
{}
|
{}
|
||||||
@@ -122,30 +125,35 @@ struct rbtree_node
|
|||||||
: m_data(other.m_data)
|
: m_data(other.m_data)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
rbtree_node(BOOST_RV_REF(rbtree_node) other)
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
: m_data(boost::move(other.m_data))
|
||||||
rbtree_node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
{}
|
||||||
: m_data(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)) \
|
|
||||||
{} \
|
#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
|
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
||||||
|
rbtree_node(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
|
: m_data(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)) \
|
||||||
|
{} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#else //#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
rbtree_node()
|
|
||||||
: m_data()
|
|
||||||
{}
|
|
||||||
|
|
||||||
template<class ...Args>
|
template<class ...Args>
|
||||||
rbtree_node(Args &&...args)
|
rbtree_node(Args &&...args)
|
||||||
: m_data(boost::forward<Args>(args)...)
|
: m_data(boost::forward<Args>(args)...)
|
||||||
{}
|
{}
|
||||||
#endif//#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif//#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
rbtree_node &operator=(const rbtree_node &other)
|
rbtree_node &operator=(const rbtree_node &other)
|
||||||
{ do_assign(other.m_data); return *this; }
|
{ do_assign(other.m_data); return *this; }
|
||||||
|
|
||||||
|
rbtree_node &operator=(BOOST_RV_REF(rbtree_node) other)
|
||||||
|
{ do_move(other.m_data); return *this; }
|
||||||
|
|
||||||
T &get_data()
|
T &get_data()
|
||||||
{
|
{
|
||||||
T* ptr = reinterpret_cast<T*>(&this->m_data);
|
T* ptr = reinterpret_cast<T*>(&this->m_data);
|
||||||
@@ -179,76 +187,88 @@ struct rbtree_node
|
|||||||
void do_assign(const V &v)
|
void do_assign(const V &v)
|
||||||
{ m_data = v; }
|
{ m_data = v; }
|
||||||
|
|
||||||
public:
|
template<class A, class B>
|
||||||
template<class Convertible>
|
void do_move(std::pair<const A, B> &p)
|
||||||
static void construct(node_type *ptr, BOOST_FWD_REF(Convertible) convertible)
|
{
|
||||||
{ new(ptr) node_type(boost::forward<Convertible>(convertible)); }
|
const_cast<A&>(m_data.first) = boost::move(p.first);
|
||||||
|
m_data.second = boost::move(p.second);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class A, class B>
|
||||||
|
void do_move(pair<const A, B> &p)
|
||||||
|
{
|
||||||
|
const_cast<A&>(m_data.first) = boost::move(p.first);
|
||||||
|
m_data.second = boost::move(p.second);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class V>
|
||||||
|
void do_move(V &v)
|
||||||
|
{ m_data = boost::move(v); }
|
||||||
};
|
};
|
||||||
|
|
||||||
}//namespace containers_detail {
|
}//namespace container_detail {
|
||||||
#if defined(BOOST_NO_RVALUE_REFERENCES)
|
|
||||||
template<class T, class VoidPointer>
|
namespace container_detail {
|
||||||
struct has_own_construct_from_it
|
|
||||||
< boost::container::containers_detail::rbtree_node<T, VoidPointer> >
|
|
||||||
{
|
|
||||||
static const bool value = true;
|
|
||||||
};
|
|
||||||
#endif
|
|
||||||
namespace containers_detail {
|
|
||||||
|
|
||||||
template<class A, class ValueCompare>
|
template<class A, class ValueCompare>
|
||||||
struct intrusive_rbtree_type
|
struct intrusive_rbtree_type
|
||||||
{
|
{
|
||||||
typedef typename A::value_type value_type;
|
typedef typename boost::container::
|
||||||
typedef typename boost::pointer_to_other
|
allocator_traits<A>::value_type value_type;
|
||||||
<typename A::pointer, void>::type void_pointer;
|
typedef typename boost::container::
|
||||||
typedef typename containers_detail::rbtree_node
|
allocator_traits<A>::void_pointer void_pointer;
|
||||||
|
typedef typename boost::container::
|
||||||
|
allocator_traits<A>::size_type size_type;
|
||||||
|
typedef typename container_detail::rbtree_node
|
||||||
<value_type, void_pointer> node_type;
|
<value_type, void_pointer> node_type;
|
||||||
typedef node_compare<ValueCompare, node_type> node_compare_type;
|
typedef node_compare<ValueCompare, node_type> node_compare_type;
|
||||||
typedef typename containers_detail::bi::make_rbtree
|
typedef typename container_detail::bi::make_rbtree
|
||||||
<node_type
|
<node_type
|
||||||
,containers_detail::bi::compare<node_compare_type>
|
,container_detail::bi::compare<node_compare_type>
|
||||||
,containers_detail::bi::base_hook<typename rbtree_hook<void_pointer>::type>
|
,container_detail::bi::base_hook<typename rbtree_hook<void_pointer>::type>
|
||||||
,containers_detail::bi::constant_time_size<true>
|
,container_detail::bi::constant_time_size<true>
|
||||||
,containers_detail::bi::size_type<typename A::size_type>
|
,container_detail::bi::size_type<size_type>
|
||||||
>::type container_type;
|
>::type container_type;
|
||||||
typedef container_type type ;
|
typedef container_type type ;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
|
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template <class Key, class Value, class KeyOfValue,
|
template <class Key, class Value, class KeyOfValue,
|
||||||
class KeyCompare, class A>
|
class KeyCompare, class A>
|
||||||
class rbtree
|
class rbtree
|
||||||
: protected containers_detail::node_alloc_holder
|
: protected container_detail::node_alloc_holder
|
||||||
<A, typename containers_detail::intrusive_rbtree_type
|
< A
|
||||||
|
, typename container_detail::intrusive_rbtree_type
|
||||||
<A, value_compare_impl<Key, Value, KeyCompare, KeyOfValue>
|
<A, value_compare_impl<Key, Value, KeyCompare, KeyOfValue>
|
||||||
>::type
|
>::type
|
||||||
|
, KeyCompare
|
||||||
>
|
>
|
||||||
{
|
{
|
||||||
typedef typename containers_detail::intrusive_rbtree_type
|
typedef typename container_detail::intrusive_rbtree_type
|
||||||
<A, value_compare_impl
|
< A, value_compare_impl
|
||||||
<Key, Value, KeyCompare, KeyOfValue>
|
<Key, Value, KeyCompare, KeyOfValue>
|
||||||
>::type Icont;
|
>::type Icont;
|
||||||
typedef containers_detail::node_alloc_holder<A, Icont> AllocHolder;
|
typedef container_detail::node_alloc_holder
|
||||||
typedef typename AllocHolder::NodePtr NodePtr;
|
<A, Icont, KeyCompare> AllocHolder;
|
||||||
|
typedef typename AllocHolder::NodePtr NodePtr;
|
||||||
typedef rbtree < Key, Value, KeyOfValue
|
typedef rbtree < Key, Value, KeyOfValue
|
||||||
, KeyCompare, A> ThisType;
|
, KeyCompare, A> ThisType;
|
||||||
typedef typename AllocHolder::NodeAlloc NodeAlloc;
|
typedef typename AllocHolder::NodeAlloc NodeAlloc;
|
||||||
typedef typename AllocHolder::ValAlloc ValAlloc;
|
typedef typename AllocHolder::ValAlloc ValAlloc;
|
||||||
typedef typename AllocHolder::Node Node;
|
typedef typename AllocHolder::Node Node;
|
||||||
typedef typename Icont::iterator iiterator;
|
typedef typename Icont::iterator iiterator;
|
||||||
typedef typename Icont::const_iterator iconst_iterator;
|
typedef typename Icont::const_iterator iconst_iterator;
|
||||||
typedef containers_detail::allocator_destroyer<NodeAlloc> Destroyer;
|
typedef container_detail::allocator_destroyer<NodeAlloc> Destroyer;
|
||||||
typedef typename AllocHolder::allocator_v1 allocator_v1;
|
typedef typename AllocHolder::allocator_v1 allocator_v1;
|
||||||
typedef typename AllocHolder::allocator_v2 allocator_v2;
|
typedef typename AllocHolder::allocator_v2 allocator_v2;
|
||||||
typedef typename AllocHolder::alloc_version alloc_version;
|
typedef typename AllocHolder::alloc_version alloc_version;
|
||||||
|
|
||||||
class RecyclingCloner;
|
class RecyclingCloner;
|
||||||
friend class RecyclingCloner;
|
friend class RecyclingCloner;
|
||||||
|
|
||||||
class RecyclingCloner
|
class RecyclingCloner
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
@@ -258,10 +278,8 @@ class rbtree
|
|||||||
|
|
||||||
NodePtr operator()(const Node &other) const
|
NodePtr operator()(const Node &other) const
|
||||||
{
|
{
|
||||||
// if(!m_icont.empty()){
|
|
||||||
if(NodePtr p = m_icont.unlink_leftmost_without_rebalance()){
|
if(NodePtr p = m_icont.unlink_leftmost_without_rebalance()){
|
||||||
//First recycle a node (this can't throw)
|
//First recycle a node (this can't throw)
|
||||||
//NodePtr p = m_icont.unlink_leftmost_without_rebalance();
|
|
||||||
try{
|
try{
|
||||||
//This can throw
|
//This can throw
|
||||||
*p = other;
|
*p = other;
|
||||||
@@ -284,6 +302,44 @@ class rbtree
|
|||||||
AllocHolder &m_holder;
|
AllocHolder &m_holder;
|
||||||
Icont &m_icont;
|
Icont &m_icont;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class RecyclingMoveCloner;
|
||||||
|
friend class RecyclingMoveCloner;
|
||||||
|
|
||||||
|
class RecyclingMoveCloner
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
RecyclingMoveCloner(AllocHolder &holder, Icont &irbtree)
|
||||||
|
: m_holder(holder), m_icont(irbtree)
|
||||||
|
{}
|
||||||
|
|
||||||
|
NodePtr operator()(const Node &other) const
|
||||||
|
{
|
||||||
|
if(NodePtr p = m_icont.unlink_leftmost_without_rebalance()){
|
||||||
|
//First recycle a node (this can't throw)
|
||||||
|
try{
|
||||||
|
//This can throw
|
||||||
|
*p = boost::move(other);
|
||||||
|
return p;
|
||||||
|
}
|
||||||
|
catch(...){
|
||||||
|
//If there is an exception destroy the whole source
|
||||||
|
m_holder.destroy_node(p);
|
||||||
|
while((p = m_icont.unlink_leftmost_without_rebalance())){
|
||||||
|
m_holder.destroy_node(p);
|
||||||
|
}
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
return m_holder.create_node(other);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
AllocHolder &m_holder;
|
||||||
|
Icont &m_icont;
|
||||||
|
};
|
||||||
|
|
||||||
BOOST_COPYABLE_AND_MOVABLE(rbtree)
|
BOOST_COPYABLE_AND_MOVABLE(rbtree)
|
||||||
|
|
||||||
public:
|
public:
|
||||||
@@ -294,12 +350,18 @@ class rbtree
|
|||||||
typedef KeyCompare key_compare;
|
typedef KeyCompare key_compare;
|
||||||
typedef value_compare_impl< Key, Value
|
typedef value_compare_impl< Key, Value
|
||||||
, KeyCompare, KeyOfValue> value_compare;
|
, KeyCompare, KeyOfValue> value_compare;
|
||||||
typedef typename A::pointer pointer;
|
typedef typename boost::container::
|
||||||
typedef typename A::const_pointer const_pointer;
|
allocator_traits<A>::pointer pointer;
|
||||||
typedef typename A::reference reference;
|
typedef typename boost::container::
|
||||||
typedef typename A::const_reference const_reference;
|
allocator_traits<A>::const_pointer const_pointer;
|
||||||
typedef typename A::size_type size_type;
|
typedef typename boost::container::
|
||||||
typedef typename A::difference_type difference_type;
|
allocator_traits<A>::reference reference;
|
||||||
|
typedef typename boost::container::
|
||||||
|
allocator_traits<A>::const_reference const_reference;
|
||||||
|
typedef typename boost::container::
|
||||||
|
allocator_traits<A>::size_type size_type;
|
||||||
|
typedef typename boost::container::
|
||||||
|
allocator_traits<A>::difference_type difference_type;
|
||||||
typedef difference_type rbtree_difference_type;
|
typedef difference_type rbtree_difference_type;
|
||||||
typedef pointer rbtree_pointer;
|
typedef pointer rbtree_pointer;
|
||||||
typedef const_pointer rbtree_const_pointer;
|
typedef const_pointer rbtree_const_pointer;
|
||||||
@@ -436,8 +498,11 @@ class rbtree
|
|||||||
typedef std::reverse_iterator<iterator> reverse_iterator;
|
typedef std::reverse_iterator<iterator> reverse_iterator;
|
||||||
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
||||||
|
|
||||||
rbtree(const key_compare& comp = key_compare(),
|
rbtree()
|
||||||
const allocator_type& a = allocator_type())
|
: AllocHolder(key_compare())
|
||||||
|
{}
|
||||||
|
|
||||||
|
rbtree(const key_compare& comp, const allocator_type& a = allocator_type())
|
||||||
: AllocHolder(a, comp)
|
: AllocHolder(a, comp)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
@@ -467,26 +532,32 @@ class rbtree
|
|||||||
}
|
}
|
||||||
|
|
||||||
rbtree(BOOST_RV_REF(rbtree) x)
|
rbtree(BOOST_RV_REF(rbtree) x)
|
||||||
: AllocHolder(x, x.key_comp())
|
: AllocHolder(boost::move(static_cast<AllocHolder&>(x)), x.key_comp())
|
||||||
{ this->swap(x); }
|
{}
|
||||||
|
|
||||||
~rbtree()
|
~rbtree()
|
||||||
{} //AllocHolder clears the tree
|
{} //AllocHolder clears the tree
|
||||||
|
|
||||||
rbtree& operator=(BOOST_COPY_ASSIGN_REF(rbtree) x)
|
rbtree& operator=(BOOST_COPY_ASSIGN_REF(rbtree) x)
|
||||||
{
|
{
|
||||||
if (this != &x) {
|
if (&x != this){
|
||||||
|
NodeAlloc &this_alloc = this->get_stored_allocator();
|
||||||
|
const NodeAlloc &x_alloc = x.get_stored_allocator();
|
||||||
|
container_detail::bool_<allocator_traits<NodeAlloc>::
|
||||||
|
propagate_on_container_copy_assignment::value> flag;
|
||||||
|
if(flag && this_alloc != x_alloc){
|
||||||
|
this->clear();
|
||||||
|
}
|
||||||
|
this->AllocHolder::copy_assign_alloc(x);
|
||||||
//Transfer all the nodes to a temporary tree
|
//Transfer all the nodes to a temporary tree
|
||||||
//If anything goes wrong, all the nodes will be destroyed
|
//If anything goes wrong, all the nodes will be destroyed
|
||||||
//automatically
|
//automatically
|
||||||
Icont other_tree(this->icont().value_comp());
|
Icont other_tree(boost::move(this->icont()));
|
||||||
other_tree.swap(this->icont());
|
|
||||||
|
|
||||||
//Now recreate the source tree reusing nodes stored by other_tree
|
//Now recreate the source tree reusing nodes stored by other_tree
|
||||||
this->icont().clone_from
|
this->icont().clone_from
|
||||||
(x.icont()
|
(x.icont()
|
||||||
, RecyclingCloner(*this, other_tree)
|
, RecyclingCloner(*this, other_tree)
|
||||||
//, AllocHolder::cloner(*this)
|
|
||||||
, Destroyer(this->node_alloc()));
|
, Destroyer(this->node_alloc()));
|
||||||
|
|
||||||
//If there are remaining nodes, destroy them
|
//If there are remaining nodes, destroy them
|
||||||
@@ -498,8 +569,41 @@ class rbtree
|
|||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
rbtree& operator=(BOOST_RV_REF(rbtree) mx)
|
rbtree& operator=(BOOST_RV_REF(rbtree) x)
|
||||||
{ this->clear(); this->swap(mx); return *this; }
|
{
|
||||||
|
if (&x != this){
|
||||||
|
NodeAlloc &this_alloc = this->node_alloc();
|
||||||
|
NodeAlloc &x_alloc = x.node_alloc();
|
||||||
|
//If allocators are equal we can just swap pointers
|
||||||
|
if(this_alloc == x_alloc){
|
||||||
|
//Destroy and swap pointers
|
||||||
|
this->clear();
|
||||||
|
this->icont() = boost::move(x.icont());
|
||||||
|
//Move allocator if needed
|
||||||
|
this->AllocHolder::move_assign_alloc(x);
|
||||||
|
}
|
||||||
|
//If unequal allocators, then do a one by one move
|
||||||
|
else{
|
||||||
|
//Transfer all the nodes to a temporary tree
|
||||||
|
//If anything goes wrong, all the nodes will be destroyed
|
||||||
|
//automatically
|
||||||
|
Icont other_tree(boost::move(this->icont()));
|
||||||
|
|
||||||
|
//Now recreate the source tree reusing nodes stored by other_tree
|
||||||
|
this->icont().clone_from
|
||||||
|
(x.icont()
|
||||||
|
, RecyclingMoveCloner(*this, other_tree)
|
||||||
|
, Destroyer(this->node_alloc()));
|
||||||
|
|
||||||
|
//If there are remaining nodes, destroy them
|
||||||
|
NodePtr p;
|
||||||
|
while((p = other_tree.unlink_leftmost_without_rebalance())){
|
||||||
|
AllocHolder::destroy_node(p);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
// accessors:
|
// accessors:
|
||||||
@@ -677,7 +781,7 @@ class rbtree
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
template <class... Args>
|
template <class... Args>
|
||||||
iterator emplace_unique(Args&&... args)
|
iterator emplace_unique(Args&&... args)
|
||||||
@@ -701,59 +805,43 @@ class rbtree
|
|||||||
return iterator(this->icont().insert_equal(hint.get(), *p));
|
return iterator(this->icont().insert_equal(hint.get(), *p));
|
||||||
}
|
}
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator emplace_unique()
|
|
||||||
{ return this->emplace_unique_impl(AllocHolder::create_node()); }
|
|
||||||
|
|
||||||
iterator emplace_hint_unique(const_iterator hint)
|
|
||||||
{ return this->emplace_unique_hint_impl(hint, AllocHolder::create_node()); }
|
|
||||||
|
|
||||||
iterator emplace_equal()
|
|
||||||
{
|
|
||||||
NodePtr p(AllocHolder::create_node());
|
|
||||||
return iterator(this->icont().insert_equal(this->icont().end(), *p));
|
|
||||||
}
|
|
||||||
|
|
||||||
iterator emplace_hint_equal(const_iterator hint)
|
|
||||||
{
|
|
||||||
NodePtr p(AllocHolder::create_node());
|
|
||||||
return iterator(this->icont().insert_equal(hint.get(), *p));
|
|
||||||
}
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
iterator emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
return this->emplace_unique_impl \
|
return this->emplace_unique_impl \
|
||||||
(AllocHolder::create_node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _))); \
|
(AllocHolder::create_node(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _))); \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_hint_unique(const_iterator hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
iterator emplace_hint_unique(const_iterator hint \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
return this->emplace_unique_hint_impl \
|
return this->emplace_unique_hint_impl \
|
||||||
(hint, AllocHolder::create_node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _))); \
|
(hint, AllocHolder::create_node(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _))); \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
iterator emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
NodePtr p(AllocHolder::create_node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _))); \
|
NodePtr p(AllocHolder::create_node(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _))); \
|
||||||
return iterator(this->icont().insert_equal(this->icont().end(), *p)); \
|
return iterator(this->icont().insert_equal(this->icont().end(), *p)); \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_hint_equal(const_iterator hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
iterator emplace_hint_equal(const_iterator hint \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
NodePtr p(AllocHolder::create_node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _))); \
|
NodePtr p(AllocHolder::create_node(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _))); \
|
||||||
return iterator(this->icont().insert_equal(hint.get(), *p)); \
|
return iterator(this->icont().insert_equal(hint.get(), *p)); \
|
||||||
} \
|
} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator insert_unique(const_iterator hint, const value_type& v)
|
iterator insert_unique(const_iterator hint, const value_type& v)
|
||||||
{
|
{
|
||||||
@@ -1044,7 +1132,7 @@ swap(rbtree<Key,Value,KeyOfValue,KeyCompare,A>& x,
|
|||||||
x.swap(y);
|
x.swap(y);
|
||||||
}
|
}
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
/*
|
/*
|
||||||
//!has_trivial_destructor_after_move<> == true_type
|
//!has_trivial_destructor_after_move<> == true_type
|
||||||
@@ -1052,7 +1140,7 @@ swap(rbtree<Key,Value,KeyOfValue,KeyCompare,A>& x,
|
|||||||
template <class K, class V, class KOV,
|
template <class K, class V, class KOV,
|
||||||
class C, class A>
|
class C, class A>
|
||||||
struct has_trivial_destructor_after_move
|
struct has_trivial_destructor_after_move
|
||||||
<boost::container::containers_detail::rbtree<K, V, KOV, C, A> >
|
<boost::container::container_detail::rbtree<K, V, KOV, C, A> >
|
||||||
{
|
{
|
||||||
static const bool value = has_trivial_destructor<A>::value && has_trivial_destructor<C>::value;
|
static const bool value = has_trivial_destructor<A>::value && has_trivial_destructor<C>::value;
|
||||||
};
|
};
|
||||||
@@ -1061,4 +1149,4 @@ struct has_trivial_destructor_after_move
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //BOOST_CONTAINERS_TREE_HPP
|
#endif //BOOST_CONTAINER_TREE_HPP
|
||||||
|
@@ -12,8 +12,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_CONTAINER_DETAIL_TYPE_TRAITS_HPP
|
#ifndef BOOST_CONTAINER_CONTAINER_DETAIL_TYPE_TRAITS_HPP
|
||||||
#define BOOST_CONTAINERS_CONTAINER_DETAIL_TYPE_TRAITS_HPP
|
#define BOOST_CONTAINER_CONTAINER_DETAIL_TYPE_TRAITS_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -25,7 +25,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
struct nat{};
|
struct nat{};
|
||||||
|
|
||||||
@@ -194,10 +194,10 @@ struct remove_ref_const
|
|||||||
typedef typename remove_const< typename remove_reference<T>::type >::type type;
|
typedef typename remove_const< typename remove_reference<T>::type >::type type;
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace containers_detail
|
} // namespace container_detail
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_CONTAINER_DETAIL_TYPE_TRAITS_HPP
|
#endif //#ifndef BOOST_CONTAINER_CONTAINER_DETAIL_TYPE_TRAITS_HPP
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_UTILITIES_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_UTILITIES_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_UTILITIES_HPP
|
#define BOOST_CONTAINER_DETAIL_UTILITIES_HPP
|
||||||
|
|
||||||
#include "config_begin.hpp"
|
#include "config_begin.hpp"
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
@@ -21,11 +21,12 @@
|
|||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
#include <boost/container/detail/mpl.hpp>
|
#include <boost/container/detail/mpl.hpp>
|
||||||
#include <boost/container/detail/type_traits.hpp>
|
#include <boost/container/detail/type_traits.hpp>
|
||||||
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class T>
|
template<class T>
|
||||||
const T &max_value(const T &a, const T &b)
|
const T &max_value(const T &a, const T &b)
|
||||||
@@ -55,29 +56,14 @@ SizeType
|
|||||||
return max_size;
|
return max_size;
|
||||||
}
|
}
|
||||||
|
|
||||||
template<class SmartPtr>
|
template <class T>
|
||||||
struct smart_ptr_type
|
inline T* to_raw_pointer(T* p)
|
||||||
{
|
{ return p; }
|
||||||
typedef typename SmartPtr::value_type value_type;
|
|
||||||
typedef value_type *pointer;
|
|
||||||
static pointer get (const SmartPtr &smartptr)
|
|
||||||
{ return smartptr.get();}
|
|
||||||
};
|
|
||||||
|
|
||||||
template<class T>
|
template <class Pointer>
|
||||||
struct smart_ptr_type<T*>
|
inline typename Pointer::element_type*
|
||||||
{
|
to_raw_pointer(const Pointer &p)
|
||||||
typedef T value_type;
|
{ return boost::container::container_detail::to_raw_pointer(p.operator->()); }
|
||||||
typedef value_type *pointer;
|
|
||||||
static pointer get (pointer ptr)
|
|
||||||
{ return ptr;}
|
|
||||||
};
|
|
||||||
|
|
||||||
//!Overload for smart pointers to avoid ADL problems with get_pointer
|
|
||||||
template<class Ptr>
|
|
||||||
inline typename smart_ptr_type<Ptr>::pointer
|
|
||||||
get_pointer(const Ptr &ptr)
|
|
||||||
{ return smart_ptr_type<Ptr>::get(ptr); }
|
|
||||||
|
|
||||||
//!To avoid ADL problems with swap
|
//!To avoid ADL problems with swap
|
||||||
template <class T>
|
template <class T>
|
||||||
@@ -87,6 +73,33 @@ inline void do_swap(T& x, T& y)
|
|||||||
swap(x, y);
|
swap(x, y);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<class AllocatorType>
|
||||||
|
inline void swap_alloc(AllocatorType &, AllocatorType &, container_detail::false_type)
|
||||||
|
BOOST_CONTAINER_NOEXCEPT
|
||||||
|
{}
|
||||||
|
|
||||||
|
template<class AllocatorType>
|
||||||
|
inline void swap_alloc(AllocatorType &l, AllocatorType &r, container_detail::true_type)
|
||||||
|
{ container_detail::do_swap(l, r); }
|
||||||
|
|
||||||
|
template<class AllocatorType>
|
||||||
|
inline void assign_alloc(AllocatorType &, const AllocatorType &, container_detail::false_type)
|
||||||
|
BOOST_CONTAINER_NOEXCEPT
|
||||||
|
{}
|
||||||
|
|
||||||
|
template<class AllocatorType>
|
||||||
|
inline void assign_alloc(AllocatorType &l, const AllocatorType &r, container_detail::true_type)
|
||||||
|
{ l = r; }
|
||||||
|
|
||||||
|
template<class AllocatorType>
|
||||||
|
inline void move_alloc(AllocatorType &, AllocatorType &, container_detail::false_type)
|
||||||
|
BOOST_CONTAINER_NOEXCEPT
|
||||||
|
{}
|
||||||
|
|
||||||
|
template<class AllocatorType>
|
||||||
|
inline void move_alloc(AllocatorType &l, AllocatorType &r, container_detail::true_type)
|
||||||
|
{ l = ::boost::move(r); }
|
||||||
|
|
||||||
//Rounds "orig_size" by excess to round_to bytes
|
//Rounds "orig_size" by excess to round_to bytes
|
||||||
template<class SizeType>
|
template<class SizeType>
|
||||||
inline SizeType get_rounded_size(SizeType orig_size, SizeType round_to)
|
inline SizeType get_rounded_size(SizeType orig_size, SizeType round_to)
|
||||||
@@ -99,36 +112,36 @@ struct ct_rounded_size
|
|||||||
{
|
{
|
||||||
enum { value = ((OrigSize-1)/RoundTo+1)*RoundTo };
|
enum { value = ((OrigSize-1)/RoundTo+1)*RoundTo };
|
||||||
};
|
};
|
||||||
|
/*
|
||||||
template <class _TypeT>
|
template <class _TypeT>
|
||||||
struct __rw_is_enum
|
struct __rw_is_enum
|
||||||
{
|
{
|
||||||
struct _C_no { };
|
struct _C_no { };
|
||||||
struct _C_yes { int _C_dummy [2]; };
|
struct _C_yes { int _C_dummy [2]; };
|
||||||
|
|
||||||
struct _C_indirect {
|
struct _C_indirect {
|
||||||
// prevent classes with user-defined conversions from matching
|
// prevent classes with user-defined conversions from matching
|
||||||
|
|
||||||
// use double to prevent float->int gcc conversion warnings
|
// use double to prevent float->int gcc conversion warnings
|
||||||
_C_indirect (double);
|
_C_indirect (double);
|
||||||
};
|
};
|
||||||
|
|
||||||
// nested struct gets rid of bogus gcc errors
|
// nested struct gets rid of bogus gcc errors
|
||||||
struct _C_nest {
|
struct _C_nest {
|
||||||
// supply first argument to prevent HP aCC warnings
|
// supply first argument to prevent HP aCC warnings
|
||||||
static _C_no _C_is (int, ...);
|
static _C_no _C_is (int, ...);
|
||||||
static _C_yes _C_is (int, _C_indirect);
|
static _C_yes _C_is (int, _C_indirect);
|
||||||
|
|
||||||
static _TypeT _C_make_T ();
|
static _TypeT _C_make_T ();
|
||||||
};
|
};
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
_C_val = sizeof (_C_yes)
|
_C_val = sizeof (_C_yes) == sizeof (_C_nest::_C_is (0, _C_nest::_C_make_T ()))
|
||||||
== sizeof (_C_nest::_C_is (0, _C_nest::_C_make_T ()))
|
&& !::boost::is_fundamental<_TypeT>::value
|
||||||
&& !::boost::is_fundamental<_TypeT>::value
|
|
||||||
};
|
};
|
||||||
|
|
||||||
};
|
};
|
||||||
|
*/
|
||||||
|
|
||||||
template<class T>
|
template<class T>
|
||||||
struct move_const_ref_type
|
struct move_const_ref_type
|
||||||
@@ -140,11 +153,119 @@ struct move_const_ref_type
|
|||||||
>
|
>
|
||||||
{};
|
{};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// uninitialized_move_alloc
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
//! <b>Effects</b>:
|
||||||
|
//! \code
|
||||||
|
//! for (; first != last; ++result, ++first)
|
||||||
|
//! allocator_traits::construct(a, &*result, boost::move(*first));
|
||||||
|
//! \endcode
|
||||||
|
//!
|
||||||
|
//! <b>Returns</b>: result
|
||||||
|
template
|
||||||
|
<typename A,
|
||||||
|
typename I, // I models InputIterator
|
||||||
|
typename F> // F models ForwardIterator
|
||||||
|
F uninitialized_move_alloc(A &a, I f, I l, F r)
|
||||||
|
{
|
||||||
|
while (f != l) {
|
||||||
|
allocator_traits<A>::construct(a, container_detail::to_raw_pointer(&*r), boost::move(*f));
|
||||||
|
++f; ++r;
|
||||||
|
}
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// uninitialized_copy_alloc
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
//! <b>Effects</b>:
|
||||||
|
//! \code
|
||||||
|
//! for (; first != last; ++result, ++first)
|
||||||
|
//! allocator_traits::construct(a, &*result, *first);
|
||||||
|
//! \endcode
|
||||||
|
//!
|
||||||
|
//! <b>Returns</b>: result
|
||||||
|
template
|
||||||
|
<typename A,
|
||||||
|
typename I, // I models InputIterator
|
||||||
|
typename F> // F models ForwardIterator
|
||||||
|
F uninitialized_copy_alloc(A &a, I f, I l, F r)
|
||||||
|
{
|
||||||
|
while (f != l) {
|
||||||
|
allocator_traits<A>::construct(a, container_detail::to_raw_pointer(&*r), *f);
|
||||||
|
++f; ++r;
|
||||||
|
}
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// uninitialized_copy_alloc
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
//! <b>Effects</b>:
|
||||||
|
//! \code
|
||||||
|
//! for (; first != last; ++result, ++first)
|
||||||
|
//! allocator_traits::construct(a, &*result, *first);
|
||||||
|
//! \endcode
|
||||||
|
//!
|
||||||
|
//! <b>Returns</b>: result
|
||||||
|
template
|
||||||
|
<typename A,
|
||||||
|
typename F, // F models ForwardIterator
|
||||||
|
typename T>
|
||||||
|
void uninitialized_fill_alloc(A &a, F f, F l, const T &t)
|
||||||
|
{
|
||||||
|
while (f != l) {
|
||||||
|
allocator_traits<A>::construct(a, container_detail::to_raw_pointer(&*f), t);
|
||||||
|
++f;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// uninitialized_copy_or_move_alloc
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
template
|
||||||
|
<typename A
|
||||||
|
,typename I // I models InputIterator
|
||||||
|
,typename F> // F models ForwardIterator
|
||||||
|
F uninitialized_copy_or_move_alloc
|
||||||
|
(A &a, I f, I l, F r
|
||||||
|
,typename boost::container::container_detail::enable_if
|
||||||
|
< boost::move_detail::is_move_iterator<I> >::type* = 0)
|
||||||
|
{
|
||||||
|
return ::boost::container::uninitialized_move_alloc(a, f, l, r);
|
||||||
|
}
|
||||||
|
|
||||||
|
template
|
||||||
|
<typename A
|
||||||
|
,typename I // I models InputIterator
|
||||||
|
,typename F> // F models ForwardIterator
|
||||||
|
F uninitialized_copy_or_move_alloc
|
||||||
|
(A &a, I f, I l, F r
|
||||||
|
,typename boost::container::container_detail::disable_if
|
||||||
|
< boost::move_detail::is_move_iterator<I> >::type* = 0)
|
||||||
|
{
|
||||||
|
return ::boost::container::uninitialized_copy_alloc(a, f, l, r);
|
||||||
|
}
|
||||||
|
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_UTILITIES_HPP
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_UTILITIES_HPP
|
||||||
|
@@ -10,8 +10,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_VALUE_INIT_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_VALUE_INIT_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_VALUE_INIT_HPP
|
#define BOOST_CONTAINER_DETAIL_VALUE_INIT_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -22,7 +22,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class T>
|
template<class T>
|
||||||
struct value_init
|
struct value_init
|
||||||
@@ -31,13 +31,15 @@ struct value_init
|
|||||||
: m_t()
|
: m_t()
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
operator T &() { return m_t; }
|
||||||
|
|
||||||
T m_t;
|
T m_t;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost {
|
} //namespace boost {
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_VALUE_INIT_HPP
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_VALUE_INIT_HPP
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_VARIADIC_TEMPLATES_TOOLS_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_VARIADIC_TEMPLATES_TOOLS_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_VARIADIC_TEMPLATES_TOOLS_HPP
|
#define BOOST_CONTAINER_DETAIL_VARIADIC_TEMPLATES_TOOLS_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -22,7 +22,7 @@
|
|||||||
|
|
||||||
namespace boost {
|
namespace boost {
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<typename... Values>
|
template<typename... Values>
|
||||||
class tuple;
|
class tuple;
|
||||||
@@ -146,8 +146,8 @@ struct build_number_seq<0, index_tuple<Indexes...> >
|
|||||||
{ typedef index_tuple<Indexes...> type; };
|
{ typedef index_tuple<Indexes...> type; };
|
||||||
|
|
||||||
|
|
||||||
}}} //namespace boost { namespace container { namespace containers_detail {
|
}}} //namespace boost { namespace container { namespace container_detail {
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_VARIADIC_TEMPLATES_TOOLS_HPP
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_VARIADIC_TEMPLATES_TOOLS_HPP
|
||||||
|
@@ -13,8 +13,8 @@
|
|||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_VERSION_TYPE_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_VERSION_TYPE_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_VERSION_TYPE_HPP
|
#define BOOST_CONTAINER_DETAIL_VERSION_TYPE_HPP
|
||||||
|
|
||||||
#include "config_begin.hpp"
|
#include "config_begin.hpp"
|
||||||
|
|
||||||
@@ -23,13 +23,13 @@
|
|||||||
|
|
||||||
namespace boost{
|
namespace boost{
|
||||||
namespace container {
|
namespace container {
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
//using namespace boost;
|
//using namespace boost;
|
||||||
|
|
||||||
template <class T, unsigned V>
|
template <class T, unsigned V>
|
||||||
struct version_type
|
struct version_type
|
||||||
: public containers_detail::integral_constant<unsigned, V>
|
: public container_detail::integral_constant<unsigned, V>
|
||||||
{
|
{
|
||||||
typedef T type;
|
typedef T type;
|
||||||
|
|
||||||
@@ -39,7 +39,7 @@ struct version_type
|
|||||||
namespace impl{
|
namespace impl{
|
||||||
|
|
||||||
template <class T,
|
template <class T,
|
||||||
bool = containers_detail::is_convertible<version_type<T, 0>, typename T::version>::value>
|
bool = container_detail::is_convertible<version_type<T, 0>, typename T::version>::value>
|
||||||
struct extract_version
|
struct extract_version
|
||||||
{
|
{
|
||||||
static const unsigned value = 1;
|
static const unsigned value = 1;
|
||||||
@@ -79,14 +79,14 @@ struct version<T, true>
|
|||||||
|
|
||||||
template <class T>
|
template <class T>
|
||||||
struct version
|
struct version
|
||||||
: public containers_detail::integral_constant<unsigned, impl::version<T>::value>
|
: public container_detail::integral_constant<unsigned, impl::version<T>::value>
|
||||||
{
|
{
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
} //namespace container {
|
} //namespace container {
|
||||||
} //namespace boost{
|
} //namespace boost{
|
||||||
|
|
||||||
#include "config_end.hpp"
|
#include "config_end.hpp"
|
||||||
|
|
||||||
#endif //#define BOOST_CONTAINERS_DETAIL_VERSION_TYPE_HPP
|
#endif //#define BOOST_CONTAINER_DETAIL_VERSION_TYPE_HPP
|
||||||
|
@@ -8,17 +8,24 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_DETAIL_WORKAROUND_HPP
|
#ifndef BOOST_CONTAINER_DETAIL_WORKAROUND_HPP
|
||||||
#define BOOST_CONTAINERS_DETAIL_WORKAROUND_HPP
|
#define BOOST_CONTAINER_DETAIL_WORKAROUND_HPP
|
||||||
|
|
||||||
#include "config_begin.hpp"
|
#include <boost/container/detail/config_begin.hpp>
|
||||||
|
|
||||||
#if !defined(BOOST_NO_RVALUE_REFERENCES) && !defined(BOOST_NO_VARIADIC_TEMPLATES)\
|
#if !defined(BOOST_NO_RVALUE_REFERENCES) && !defined(BOOST_NO_VARIADIC_TEMPLATES)\
|
||||||
&& !defined(BOOST_INTERPROCESS_DISABLE_VARIADIC_TMPL)
|
&& !defined(BOOST_INTERPROCESS_DISABLE_VARIADIC_TMPL)
|
||||||
#define BOOST_CONTAINERS_PERFECT_FORWARDING
|
#define BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(BOOST_NO_NOEXCEPT)
|
||||||
|
#define BOOST_CONTAINER_NOEXCEPT
|
||||||
|
#define BOOST_CONTAINER_NOEXCEPT_IF(x)
|
||||||
|
#else
|
||||||
|
#define BOOST_CONTAINER_NOEXCEPT noexcept
|
||||||
|
#define BOOST_CONTAINER_NOEXCEPT_IF(x) noexcept(x)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif //#ifndef BOOST_CONTAINERS_DETAIL_WORKAROUND_HPP
|
#endif //#ifndef BOOST_CONTAINER_DETAIL_WORKAROUND_HPP
|
||||||
|
File diff suppressed because it is too large
Load Diff
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_FLAT_SET_HPP
|
#ifndef BOOST_CONTAINER_FLAT_SET_HPP
|
||||||
#define BOOST_CONTAINERS_FLAT_SET_HPP
|
#define BOOST_CONTAINER_FLAT_SET_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -74,9 +74,9 @@ class flat_set
|
|||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
BOOST_COPYABLE_AND_MOVABLE(flat_set)
|
BOOST_COPYABLE_AND_MOVABLE(flat_set)
|
||||||
typedef containers_detail::flat_tree<T, T, containers_detail::identity<T>, Pred, A> tree_t;
|
typedef container_detail::flat_tree<T, T, container_detail::identity<T>, Pred, A> tree_t;
|
||||||
tree_t m_flat_tree; // flat tree representing flat_set
|
tree_t m_flat_tree; // flat tree representing flat_set
|
||||||
typedef typename containers_detail::
|
typedef typename container_detail::
|
||||||
move_const_ref_type<T>::type insert_const_ref_type;
|
move_const_ref_type<T>::type insert_const_ref_type;
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
@@ -100,11 +100,18 @@ class flat_set
|
|||||||
typedef typename tree_t::allocator_type allocator_type;
|
typedef typename tree_t::allocator_type allocator_type;
|
||||||
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Defatuls constructs an empty flat_map.
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
explicit flat_set()
|
||||||
|
: m_flat_tree()
|
||||||
|
{}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs an empty flat_map using the specified
|
//! <b>Effects</b>: Constructs an empty flat_map using the specified
|
||||||
//! comparison object and allocator.
|
//! comparison object and allocator.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
explicit flat_set(const Pred& comp = Pred(),
|
explicit flat_set(const Pred& comp,
|
||||||
const allocator_type& a = allocator_type())
|
const allocator_type& a = allocator_type())
|
||||||
: m_flat_tree(comp, a)
|
: m_flat_tree(comp, a)
|
||||||
{}
|
{}
|
||||||
@@ -317,7 +324,6 @@ class flat_set
|
|||||||
{ return m_flat_tree.max_size(); }
|
{ return m_flat_tree.max_size(); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type() allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -335,7 +341,7 @@ class flat_set
|
|||||||
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
||||||
//! to the elements with bigger keys than x.
|
//! to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
std::pair<iterator, bool> insert(insert_const_ref_type x)
|
std::pair<iterator, bool> insert(insert_const_ref_type x)
|
||||||
{ return priv_insert(x); }
|
{ return priv_insert(x); }
|
||||||
|
|
||||||
@@ -344,7 +350,7 @@ class flat_set
|
|||||||
{ return this->insert(const_cast<const T &>(x)); }
|
{ return this->insert(const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
std::pair<iterator, bool> insert(const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
std::pair<iterator, bool> insert(const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_insert(u); }
|
{ return priv_insert(u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -358,7 +364,7 @@ class flat_set
|
|||||||
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
||||||
//! to the elements with bigger keys than x.
|
//! to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
std::pair<iterator,bool> insert(BOOST_RV_REF(value_type) x)
|
std::pair<iterator,bool> insert(BOOST_RV_REF(value_type) x)
|
||||||
{ return m_flat_tree.insert_unique(boost::move(x)); }
|
{ return m_flat_tree.insert_unique(boost::move(x)); }
|
||||||
|
|
||||||
@@ -372,7 +378,7 @@ class flat_set
|
|||||||
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
||||||
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
iterator insert(const_iterator p, insert_const_ref_type x)
|
iterator insert(const_iterator p, insert_const_ref_type x)
|
||||||
{ return priv_insert(p, x); }
|
{ return priv_insert(p, x); }
|
||||||
|
|
||||||
@@ -381,7 +387,7 @@ class flat_set
|
|||||||
{ return this->insert(position, const_cast<const T &>(x)); }
|
{ return this->insert(position, const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert(const_iterator position, const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert(const_iterator position, const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_insert(position, u); }
|
{ return priv_insert(position, u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -393,7 +399,7 @@ class flat_set
|
|||||||
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
||||||
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
iterator insert(const_iterator position, BOOST_RV_REF(value_type) x)
|
iterator insert(const_iterator position, BOOST_RV_REF(value_type) x)
|
||||||
{ return m_flat_tree.insert_unique(position, boost::move(x)); }
|
{ return m_flat_tree.insert_unique(position, boost::move(x)); }
|
||||||
|
|
||||||
@@ -405,12 +411,12 @@ class flat_set
|
|||||||
//! <b>Complexity</b>: At most N log(size()+N) (N is the distance from first to last)
|
//! <b>Complexity</b>: At most N log(size()+N) (N is the distance from first to last)
|
||||||
//! search time plus N*size() insertion time.
|
//! search time plus N*size() insertion time.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
template <class InputIterator>
|
template <class InputIterator>
|
||||||
void insert(InputIterator first, InputIterator last)
|
void insert(InputIterator first, InputIterator last)
|
||||||
{ m_flat_tree.insert_unique(first, last); }
|
{ m_flat_tree.insert_unique(first, last); }
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... if and only if there is no element in the container
|
//! std::forward<Args>(args)... if and only if there is no element in the container
|
||||||
@@ -423,7 +429,7 @@ class flat_set
|
|||||||
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
||||||
//! to the elements with bigger keys than x.
|
//! to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
template <class... Args>
|
template <class... Args>
|
||||||
iterator emplace(Args&&... args)
|
iterator emplace(Args&&... args)
|
||||||
{ return m_flat_tree.emplace_unique(boost::forward<Args>(args)...); }
|
{ return m_flat_tree.emplace_unique(boost::forward<Args>(args)...); }
|
||||||
@@ -439,32 +445,28 @@ class flat_set
|
|||||||
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
||||||
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
template <class... Args>
|
template <class... Args>
|
||||||
iterator emplace_hint(const_iterator hint, Args&&... args)
|
iterator emplace_hint(const_iterator hint, Args&&... args)
|
||||||
{ return m_flat_tree.emplace_hint_unique(hint, boost::forward<Args>(args)...); }
|
{ return m_flat_tree.emplace_hint_unique(hint, boost::forward<Args>(args)...); }
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator emplace()
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
{ return m_flat_tree.emplace_unique(); }
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace_hint(const_iterator hint)
|
{ return m_flat_tree.emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
{ return m_flat_tree.emplace_hint_unique(hint); }
|
\
|
||||||
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
iterator emplace_hint(const_iterator hint \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
{ return m_flat_tree.emplace_hint_unique \
|
||||||
{ return m_flat_tree.emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); } \
|
(hint BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
\
|
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
iterator emplace_hint(const_iterator hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
{ return m_flat_tree.emplace_hint_unique(hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); }\
|
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases the element pointed to by position.
|
//! <b>Effects</b>: Erases the element pointed to by position.
|
||||||
//!
|
//!
|
||||||
@@ -702,9 +704,9 @@ class flat_multiset
|
|||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
BOOST_COPYABLE_AND_MOVABLE(flat_multiset)
|
BOOST_COPYABLE_AND_MOVABLE(flat_multiset)
|
||||||
typedef containers_detail::flat_tree<T, T, containers_detail::identity<T>, Pred, A> tree_t;
|
typedef container_detail::flat_tree<T, T, container_detail::identity<T>, Pred, A> tree_t;
|
||||||
tree_t m_flat_tree; // flat tree representing flat_multiset
|
tree_t m_flat_tree; // flat tree representing flat_multiset
|
||||||
typedef typename containers_detail::
|
typedef typename container_detail::
|
||||||
move_const_ref_type<T>::type insert_const_ref_type;
|
move_const_ref_type<T>::type insert_const_ref_type;
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
@@ -727,8 +729,14 @@ class flat_multiset
|
|||||||
typedef typename tree_t::allocator_type allocator_type;
|
typedef typename tree_t::allocator_type allocator_type;
|
||||||
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
||||||
|
|
||||||
// allocation/deallocation
|
//! <b>Effects</b>: Defatuls constructs an empty flat_map.
|
||||||
explicit flat_multiset(const Pred& comp = Pred(),
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
explicit flat_multiset()
|
||||||
|
: m_flat_tree()
|
||||||
|
{}
|
||||||
|
|
||||||
|
explicit flat_multiset(const Pred& comp,
|
||||||
const allocator_type& a = allocator_type())
|
const allocator_type& a = allocator_type())
|
||||||
: m_flat_tree(comp, a) {}
|
: m_flat_tree(comp, a) {}
|
||||||
|
|
||||||
@@ -920,7 +928,6 @@ class flat_multiset
|
|||||||
{ return m_flat_tree.max_size(); }
|
{ return m_flat_tree.max_size(); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type() allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -934,7 +941,7 @@ class flat_multiset
|
|||||||
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
||||||
//! to the elements with bigger keys than x.
|
//! to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
iterator insert(insert_const_ref_type x)
|
iterator insert(insert_const_ref_type x)
|
||||||
{ return priv_insert(x); }
|
{ return priv_insert(x); }
|
||||||
|
|
||||||
@@ -943,7 +950,7 @@ class flat_multiset
|
|||||||
{ return this->insert(const_cast<const T &>(x)); }
|
{ return this->insert(const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert(const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert(const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_insert(u); }
|
{ return priv_insert(u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -953,7 +960,7 @@ class flat_multiset
|
|||||||
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
||||||
//! to the elements with bigger keys than x.
|
//! to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
iterator insert(BOOST_RV_REF(value_type) x)
|
iterator insert(BOOST_RV_REF(value_type) x)
|
||||||
{ return m_flat_tree.insert_equal(boost::move(x)); }
|
{ return m_flat_tree.insert_equal(boost::move(x)); }
|
||||||
|
|
||||||
@@ -966,7 +973,7 @@ class flat_multiset
|
|||||||
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
||||||
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
iterator insert(const_iterator p, insert_const_ref_type x)
|
iterator insert(const_iterator p, insert_const_ref_type x)
|
||||||
{ return priv_insert(p, x); }
|
{ return priv_insert(p, x); }
|
||||||
|
|
||||||
@@ -975,7 +982,7 @@ class flat_multiset
|
|||||||
{ return this->insert(position, const_cast<const T &>(x)); }
|
{ return this->insert(position, const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert(const_iterator position, const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert(const_iterator position, const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_insert(position, u); }
|
{ return priv_insert(position, u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -988,7 +995,7 @@ class flat_multiset
|
|||||||
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
||||||
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
iterator insert(const_iterator position, BOOST_RV_REF(value_type) x)
|
iterator insert(const_iterator position, BOOST_RV_REF(value_type) x)
|
||||||
{ return m_flat_tree.insert_equal(position, boost::move(x)); }
|
{ return m_flat_tree.insert_equal(position, boost::move(x)); }
|
||||||
|
|
||||||
@@ -999,12 +1006,12 @@ class flat_multiset
|
|||||||
//! <b>Complexity</b>: At most N log(size()+N) (N is the distance from first to last)
|
//! <b>Complexity</b>: At most N log(size()+N) (N is the distance from first to last)
|
||||||
//! search time plus N*size() insertion time.
|
//! search time plus N*size() insertion time.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
template <class InputIterator>
|
template <class InputIterator>
|
||||||
void insert(InputIterator first, InputIterator last)
|
void insert(InputIterator first, InputIterator last)
|
||||||
{ m_flat_tree.insert_equal(first, last); }
|
{ m_flat_tree.insert_equal(first, last); }
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... and returns the iterator pointing to the
|
//! std::forward<Args>(args)... and returns the iterator pointing to the
|
||||||
@@ -1013,7 +1020,7 @@ class flat_multiset
|
|||||||
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
//! <b>Complexity</b>: Logarithmic search time plus linear insertion
|
||||||
//! to the elements with bigger keys than x.
|
//! to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
template <class... Args>
|
template <class... Args>
|
||||||
iterator emplace(Args&&... args)
|
iterator emplace(Args&&... args)
|
||||||
{ return m_flat_tree.emplace_equal(boost::forward<Args>(args)...); }
|
{ return m_flat_tree.emplace_equal(boost::forward<Args>(args)...); }
|
||||||
@@ -1028,32 +1035,28 @@ class flat_multiset
|
|||||||
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
//! <b>Complexity</b>: Logarithmic search time (constant if x is inserted
|
||||||
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
//! right before p) plus insertion linear to the elements with bigger keys than x.
|
||||||
//!
|
//!
|
||||||
//! <b>Note</b>: If an element it's inserted it might invalidate elements.
|
//! <b>Note</b>: If an element is inserted it might invalidate elements.
|
||||||
template <class... Args>
|
template <class... Args>
|
||||||
iterator emplace_hint(const_iterator hint, Args&&... args)
|
iterator emplace_hint(const_iterator hint, Args&&... args)
|
||||||
{ return m_flat_tree.emplace_hint_equal(hint, boost::forward<Args>(args)...); }
|
{ return m_flat_tree.emplace_hint_equal(hint, boost::forward<Args>(args)...); }
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator emplace()
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
{ return m_flat_tree.emplace_equal(); }
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace_hint(const_iterator hint)
|
{ return m_flat_tree.emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
{ return m_flat_tree.emplace_hint_equal(hint); }
|
\
|
||||||
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
iterator emplace_hint(const_iterator hint \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
{ return m_flat_tree.emplace_hint_equal \
|
||||||
{ return m_flat_tree.emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); } \
|
(hint BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
\
|
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
iterator emplace_hint(const_iterator hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
{ return m_flat_tree.emplace_hint_equal(hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); } \
|
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases the element pointed to by position.
|
//! <b>Effects</b>: Erases the element pointed to by position.
|
||||||
//!
|
//!
|
||||||
@@ -1258,4 +1261,4 @@ namespace container {
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif /* BOOST_CONTAINERS_FLAT_SET_HPP */
|
#endif /* BOOST_CONTAINER_FLAT_SET_HPP */
|
||||||
|
@@ -7,8 +7,8 @@
|
|||||||
// See http://www.boost.org/libs/container for documentation.
|
// See http://www.boost.org/libs/container for documentation.
|
||||||
//
|
//
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_LIST_HPP_
|
#ifndef BOOST_CONTAINER_LIST_HPP_
|
||||||
#define BOOST_CONTAINERS_LIST_HPP_
|
#define BOOST_CONTAINER_LIST_HPP_
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -20,15 +20,16 @@
|
|||||||
#include <boost/container/detail/version_type.hpp>
|
#include <boost/container/detail/version_type.hpp>
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
#include <boost/move/move_helpers.hpp>
|
#include <boost/move/move_helpers.hpp>
|
||||||
#include <boost/pointer_to_other.hpp>
|
#include <boost/intrusive/pointer_traits.hpp>
|
||||||
#include <boost/container/detail/utilities.hpp>
|
#include <boost/container/detail/utilities.hpp>
|
||||||
#include <boost/container/detail/algorithms.hpp>
|
#include <boost/container/detail/algorithms.hpp>
|
||||||
#include <boost/type_traits/has_trivial_destructor.hpp>
|
#include <boost/type_traits/has_trivial_destructor.hpp>
|
||||||
#include <boost/container/detail/mpl.hpp>
|
#include <boost/container/detail/mpl.hpp>
|
||||||
#include <boost/intrusive/list.hpp>
|
#include <boost/intrusive/list.hpp>
|
||||||
|
#include <boost/assert.hpp>
|
||||||
#include <boost/container/detail/node_alloc_holder.hpp>
|
#include <boost/container/detail/node_alloc_holder.hpp>
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
#else
|
#else
|
||||||
//Preprocessor library to emulate perfect forwarding
|
//Preprocessor library to emulate perfect forwarding
|
||||||
#include <boost/container/detail/preprocessor.hpp>
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
@@ -51,13 +52,13 @@ namespace container {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
/// @cond
|
/// @cond
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class VoidPointer>
|
template<class VoidPointer>
|
||||||
struct list_hook
|
struct list_hook
|
||||||
{
|
{
|
||||||
typedef typename containers_detail::bi::make_list_base_hook
|
typedef typename container_detail::bi::make_list_base_hook
|
||||||
<containers_detail::bi::void_pointer<VoidPointer>, containers_detail::bi::link_mode<containers_detail::bi::normal_link> >::type type;
|
<container_detail::bi::void_pointer<VoidPointer>, container_detail::bi::link_mode<container_detail::bi::normal_link> >::type type;
|
||||||
};
|
};
|
||||||
|
|
||||||
template <class T, class VoidPointer>
|
template <class T, class VoidPointer>
|
||||||
@@ -65,33 +66,28 @@ struct list_node
|
|||||||
: public list_hook<VoidPointer>::type
|
: public list_hook<VoidPointer>::type
|
||||||
{
|
{
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
|
||||||
|
|
||||||
list_node()
|
list_node()
|
||||||
: m_data()
|
: m_data()
|
||||||
{}
|
{}
|
||||||
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
template<class ...Args>
|
template<class ...Args>
|
||||||
list_node(Args &&...args)
|
list_node(Args &&...args)
|
||||||
: m_data(boost::forward<Args>(args)...)
|
: m_data(boost::forward<Args>(args)...)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
#else //#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
list_node()
|
|
||||||
: m_data()
|
|
||||||
{}
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
||||||
list_node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
list_node(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
: m_data(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)) \
|
: m_data(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)) \
|
||||||
{} \
|
{} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif//#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif//#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
T m_data;
|
T m_data;
|
||||||
};
|
};
|
||||||
@@ -99,21 +95,25 @@ struct list_node
|
|||||||
template<class A>
|
template<class A>
|
||||||
struct intrusive_list_type
|
struct intrusive_list_type
|
||||||
{
|
{
|
||||||
typedef typename A::value_type value_type;
|
typedef boost::container::allocator_traits<A> allocator_traits_type;
|
||||||
typedef typename boost::pointer_to_other
|
typedef typename allocator_traits_type::value_type value_type;
|
||||||
<typename A::pointer, void>::type void_pointer;
|
typedef typename boost::intrusive::pointer_traits
|
||||||
typedef typename containers_detail::list_node
|
<typename allocator_traits_type::pointer>::template
|
||||||
|
rebind_pointer<void>::type
|
||||||
|
void_pointer;
|
||||||
|
typedef typename container_detail::list_node
|
||||||
<value_type, void_pointer> node_type;
|
<value_type, void_pointer> node_type;
|
||||||
typedef typename containers_detail::bi::make_list
|
typedef typename container_detail::bi::make_list
|
||||||
< node_type
|
< node_type
|
||||||
, containers_detail::bi::base_hook<typename list_hook<void_pointer>::type>
|
, container_detail::bi::base_hook<typename list_hook<void_pointer>::type>
|
||||||
, containers_detail::bi::constant_time_size<true>
|
, container_detail::bi::constant_time_size<true>
|
||||||
, containers_detail::bi::size_type<typename A::size_type>
|
, container_detail::bi::size_type
|
||||||
|
<typename allocator_traits_type::size_type>
|
||||||
>::type container_type;
|
>::type container_type;
|
||||||
typedef container_type type ;
|
typedef container_type type ;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
//! A list is a doubly linked list. That is, it is a Sequence that supports both
|
//! A list is a doubly linked list. That is, it is a Sequence that supports both
|
||||||
@@ -132,22 +132,23 @@ template <class T, class A = std::allocator<T> >
|
|||||||
template <class T, class A>
|
template <class T, class A>
|
||||||
#endif
|
#endif
|
||||||
class list
|
class list
|
||||||
: protected containers_detail::node_alloc_holder
|
: protected container_detail::node_alloc_holder
|
||||||
<A, typename containers_detail::intrusive_list_type<A>::type>
|
<A, typename container_detail::intrusive_list_type<A>::type>
|
||||||
{
|
{
|
||||||
/// @cond
|
/// @cond
|
||||||
typedef typename
|
typedef typename
|
||||||
containers_detail::intrusive_list_type<A>::type Icont;
|
container_detail::intrusive_list_type<A>::type Icont;
|
||||||
typedef list <T, A> ThisType;
|
typedef list <T, A> ThisType;
|
||||||
typedef containers_detail::node_alloc_holder<A, Icont> AllocHolder;
|
typedef container_detail::node_alloc_holder<A, Icont> AllocHolder;
|
||||||
typedef typename AllocHolder::NodePtr NodePtr;
|
typedef typename AllocHolder::NodePtr NodePtr;
|
||||||
typedef typename AllocHolder::NodeAlloc NodeAlloc;
|
typedef typename AllocHolder::NodeAlloc NodeAlloc;
|
||||||
typedef typename AllocHolder::ValAlloc ValAlloc;
|
typedef typename AllocHolder::ValAlloc ValAlloc;
|
||||||
typedef typename AllocHolder::Node Node;
|
typedef typename AllocHolder::Node Node;
|
||||||
typedef containers_detail::allocator_destroyer<NodeAlloc> Destroyer;
|
typedef container_detail::allocator_destroyer<NodeAlloc> Destroyer;
|
||||||
typedef typename AllocHolder::allocator_v1 allocator_v1;
|
typedef typename AllocHolder::allocator_v1 allocator_v1;
|
||||||
typedef typename AllocHolder::allocator_v2 allocator_v2;
|
typedef typename AllocHolder::allocator_v2 allocator_v2;
|
||||||
typedef typename AllocHolder::alloc_version alloc_version;
|
typedef typename AllocHolder::alloc_version alloc_version;
|
||||||
|
typedef boost::container::allocator_traits<A> allocator_traits_type;
|
||||||
|
|
||||||
class equal_to_value
|
class equal_to_value
|
||||||
{
|
{
|
||||||
@@ -181,23 +182,23 @@ class list
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
//! The type of object, T, stored in the list
|
//! The type of object, T, stored in the list
|
||||||
typedef T value_type;
|
typedef T value_type;
|
||||||
//! Pointer to T
|
//! Pointer to T
|
||||||
typedef typename A::pointer pointer;
|
typedef typename allocator_traits_type::pointer pointer;
|
||||||
//! Const pointer to T
|
//! Const pointer to T
|
||||||
typedef typename A::const_pointer const_pointer;
|
typedef typename allocator_traits_type::const_pointer const_pointer;
|
||||||
//! Reference to T
|
//! Reference to T
|
||||||
typedef typename A::reference reference;
|
typedef typename allocator_traits_type::reference reference;
|
||||||
//! Const reference to T
|
//! Const reference to T
|
||||||
typedef typename A::const_reference const_reference;
|
typedef typename allocator_traits_type::const_reference const_reference;
|
||||||
//! An unsigned integral type
|
//! An unsigned integral type
|
||||||
typedef typename A::size_type size_type;
|
typedef typename allocator_traits_type::size_type size_type;
|
||||||
//! A signed integral type
|
//! A signed integral type
|
||||||
typedef typename A::difference_type difference_type;
|
typedef typename allocator_traits_type::difference_type difference_type;
|
||||||
//! The allocator type
|
//! The allocator type
|
||||||
typedef A allocator_type;
|
typedef A allocator_type;
|
||||||
//! The stored allocator type
|
//! Non-standard extension: the stored allocator type
|
||||||
typedef NodeAlloc stored_allocator_type;
|
typedef NodeAlloc stored_allocator_type;
|
||||||
|
|
||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
@@ -313,12 +314,21 @@ class list
|
|||||||
//! Const iterator used to iterate backwards through a list.
|
//! Const iterator used to iterate backwards through a list.
|
||||||
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Default constructs a list.
|
||||||
|
//!
|
||||||
|
//! <b>Throws</b>: If allocator_type's default constructor throws.
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
list()
|
||||||
|
: AllocHolder()
|
||||||
|
{}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs a list taking the allocator as parameter.
|
//! <b>Effects</b>: Constructs a list taking the allocator as parameter.
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
explicit list(const allocator_type &a = A())
|
explicit list(const allocator_type &a)
|
||||||
: AllocHolder(a)
|
: AllocHolder(a)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
@@ -329,7 +339,7 @@ class list
|
|||||||
//! throws or T's default or copy constructor throws.
|
//! throws or T's default or copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Linear to n.
|
//! <b>Complexity</b>: Linear to n.
|
||||||
list(size_type n)
|
explicit list(size_type n)
|
||||||
: AllocHolder(A())
|
: AllocHolder(A())
|
||||||
{ this->resize(n); }
|
{ this->resize(n); }
|
||||||
|
|
||||||
@@ -533,7 +543,6 @@ class list
|
|||||||
size_type max_size() const
|
size_type max_size() const
|
||||||
{ return AllocHolder::max_size(); }
|
{ return AllocHolder::max_size(); }
|
||||||
|
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
//! <b>Effects</b>: Inserts a copy of x at the beginning of the list.
|
//! <b>Effects</b>: Inserts a copy of x at the beginning of the list.
|
||||||
//!
|
//!
|
||||||
@@ -692,8 +701,6 @@ class list
|
|||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type()
|
|
||||||
//! allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -711,7 +718,15 @@ class list
|
|||||||
//! <b>Complexity</b>: Linear to the number of elements in x.
|
//! <b>Complexity</b>: Linear to the number of elements in x.
|
||||||
ThisType& operator=(BOOST_COPY_ASSIGN_REF(ThisType) x)
|
ThisType& operator=(BOOST_COPY_ASSIGN_REF(ThisType) x)
|
||||||
{
|
{
|
||||||
if (this != &x) {
|
if (&x != this){
|
||||||
|
NodeAlloc &this_alloc = this->node_alloc();
|
||||||
|
const NodeAlloc &x_alloc = x.node_alloc();
|
||||||
|
container_detail::bool_<allocator_traits_type::
|
||||||
|
propagate_on_container_copy_assignment::value> flag;
|
||||||
|
if(flag && this_alloc != x_alloc){
|
||||||
|
this->clear();
|
||||||
|
}
|
||||||
|
this->AllocHolder::copy_assign_alloc(x);
|
||||||
this->assign(x.begin(), x.end());
|
this->assign(x.begin(), x.end());
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
@@ -725,10 +740,26 @@ class list
|
|||||||
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
ThisType& operator=(BOOST_RV_REF(ThisType) mx)
|
ThisType& operator=(BOOST_RV_REF(ThisType) x)
|
||||||
{
|
{
|
||||||
this->clear();
|
if (&x != this){
|
||||||
this->swap(mx);
|
NodeAlloc &this_alloc = this->node_alloc();
|
||||||
|
NodeAlloc &x_alloc = x.node_alloc();
|
||||||
|
//If allocators are equal we can just swap pointers
|
||||||
|
if(this_alloc == x_alloc){
|
||||||
|
//Destroy and swap pointers
|
||||||
|
this->clear();
|
||||||
|
this->icont() = boost::move(x.icont());
|
||||||
|
//Move allocator if needed
|
||||||
|
this->AllocHolder::move_assign_alloc(x);
|
||||||
|
}
|
||||||
|
//If unequal allocators, then do a one by one move
|
||||||
|
else{
|
||||||
|
typedef typename std::iterator_traits<iterator>::iterator_category ItCat;
|
||||||
|
this->assign( boost::make_move_iterator(x.begin())
|
||||||
|
, boost::make_move_iterator(x.end()));
|
||||||
|
}
|
||||||
|
}
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -753,8 +784,8 @@ class list
|
|||||||
template <class InpIt>
|
template <class InpIt>
|
||||||
void insert(const_iterator p, InpIt first, InpIt last)
|
void insert(const_iterator p, InpIt first, InpIt last)
|
||||||
{
|
{
|
||||||
const bool aux_boolean = containers_detail::is_convertible<InpIt, size_type>::value;
|
const bool aux_boolean = container_detail::is_convertible<InpIt, size_type>::value;
|
||||||
typedef containers_detail::bool_<aux_boolean> Result;
|
typedef container_detail::bool_<aux_boolean> Result;
|
||||||
this->priv_insert_dispatch(p, first, last, Result());
|
this->priv_insert_dispatch(p, first, last, Result());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -780,7 +811,7 @@ class list
|
|||||||
BOOST_MOVE_CONVERSION_AWARE_CATCH_1ARG(insert, T, iterator, priv_insert, const_iterator)
|
BOOST_MOVE_CONVERSION_AWARE_CATCH_1ARG(insert, T, iterator, priv_insert, const_iterator)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... in the end of the list.
|
//! std::forward<Args>(args)... in the end of the list.
|
||||||
@@ -818,57 +849,40 @@ class list
|
|||||||
template <class... Args>
|
template <class... Args>
|
||||||
iterator emplace(const_iterator p, Args&&... args)
|
iterator emplace(const_iterator p, Args&&... args)
|
||||||
{
|
{
|
||||||
typename AllocHolder::Deallocator d(AllocHolder::create_node_and_deallocator());
|
NodePtr pnode(AllocHolder::create_node(boost::forward<Args>(args)...));
|
||||||
new ((void*)containers_detail::get_pointer(d.get())) Node(boost::forward<Args>(args)...);
|
return iterator(this->icont().insert(p.get(), *pnode));
|
||||||
NodePtr node = d.get();
|
|
||||||
d.release();
|
|
||||||
return iterator(this->icont().insert(p.get(), *node));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//0 args
|
|
||||||
void emplace_back()
|
|
||||||
{ this->emplace(this->cend()); }
|
|
||||||
|
|
||||||
void emplace_front()
|
|
||||||
{ this->emplace(this->cbegin()); }
|
|
||||||
|
|
||||||
iterator emplace(const_iterator p)
|
|
||||||
{
|
|
||||||
typename AllocHolder::Deallocator d(AllocHolder::create_node_and_deallocator());
|
|
||||||
new ((void*)containers_detail::get_pointer(d.get())) Node();
|
|
||||||
NodePtr node = d.get();
|
|
||||||
d.release();
|
|
||||||
return iterator(this->icont().insert(p.get(), *node));
|
|
||||||
}
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
void emplace_back(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
void emplace_back(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
this->emplace(this->cend(), BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
this->emplace(this->cend() \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
void emplace_front(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
void emplace_front(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ this->emplace(this->cbegin(), BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _));} \
|
|
||||||
\
|
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
iterator emplace(const_iterator p, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
{ \
|
{ \
|
||||||
typename AllocHolder::Deallocator d(AllocHolder::create_node_and_deallocator()); \
|
this->emplace(this->cbegin() \
|
||||||
new ((void*)containers_detail::get_pointer(d.get())) \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); \
|
||||||
Node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
} \
|
||||||
NodePtr node = d.get(); \
|
\
|
||||||
d.release(); \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
return iterator(this->icont().insert(p.get(), *node)); \
|
iterator emplace(const_iterator p \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
|
{ \
|
||||||
|
NodePtr pnode (AllocHolder::create_node \
|
||||||
|
(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _))); \
|
||||||
|
return iterator(this->icont().insert(p.get(), *pnode)); \
|
||||||
} \
|
} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Requires</b>: p must be a valid iterator of *this.
|
//! <b>Requires</b>: p must be a valid iterator of *this.
|
||||||
//!
|
//!
|
||||||
@@ -907,8 +921,8 @@ class list
|
|||||||
template <class InpIt>
|
template <class InpIt>
|
||||||
void assign(InpIt first, InpIt last)
|
void assign(InpIt first, InpIt last)
|
||||||
{
|
{
|
||||||
const bool aux_boolean = containers_detail::is_convertible<InpIt, size_type>::value;
|
const bool aux_boolean = container_detail::is_convertible<InpIt, size_type>::value;
|
||||||
typedef containers_detail::bool_<aux_boolean> Result;
|
typedef container_detail::bool_<aux_boolean> Result;
|
||||||
this->priv_assign_dispatch(first, last, Result());
|
this->priv_assign_dispatch(first, last, Result());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -925,14 +939,10 @@ class list
|
|||||||
//!
|
//!
|
||||||
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of
|
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of
|
||||||
//! this list. Iterators of this list and all the references are not invalidated.
|
//! this list. Iterators of this list and all the references are not invalidated.
|
||||||
void splice(const_iterator p, ThisType& x)
|
void splice(const_iterator p, ThisType& x) BOOST_CONTAINER_NOEXCEPT
|
||||||
{
|
{
|
||||||
if((NodeAlloc&)*this == (NodeAlloc&)x){
|
BOOST_ASSERT((NodeAlloc&)*this == (NodeAlloc&)x);
|
||||||
this->icont().splice(p.get(), x.icont());
|
this->icont().splice(p.get(), x.icont());
|
||||||
}
|
|
||||||
else{
|
|
||||||
throw std::runtime_error("list::splice called with unequal allocators");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Requires</b>: p must point to an element contained
|
//! <b>Requires</b>: p must point to an element contained
|
||||||
@@ -949,14 +959,10 @@ class list
|
|||||||
//!
|
//!
|
||||||
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
|
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
|
||||||
//! list. Iterators of this list and all the references are not invalidated.
|
//! list. Iterators of this list and all the references are not invalidated.
|
||||||
void splice(const_iterator p, ThisType &x, const_iterator i)
|
void splice(const_iterator p, ThisType &x, const_iterator i) BOOST_CONTAINER_NOEXCEPT
|
||||||
{
|
{
|
||||||
if((NodeAlloc&)*this == (NodeAlloc&)x){
|
BOOST_ASSERT((NodeAlloc&)*this == (NodeAlloc&)x);
|
||||||
this->icont().splice(p.get(), x.icont(), i.get());
|
this->icont().splice(p.get(), x.icont(), i.get());
|
||||||
}
|
|
||||||
else{
|
|
||||||
throw std::runtime_error("list::splice called with unequal allocators");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Requires</b>: p must point to an element contained
|
//! <b>Requires</b>: p must point to an element contained
|
||||||
@@ -972,14 +978,10 @@ class list
|
|||||||
//!
|
//!
|
||||||
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
|
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
|
||||||
//! list. Iterators of this list and all the references are not invalidated.
|
//! list. Iterators of this list and all the references are not invalidated.
|
||||||
void splice(const_iterator p, ThisType &x, const_iterator first, const_iterator last)
|
void splice(const_iterator p, ThisType &x, const_iterator first, const_iterator last) BOOST_CONTAINER_NOEXCEPT
|
||||||
{
|
{
|
||||||
if((NodeAlloc&)*this == (NodeAlloc&)x){
|
BOOST_ASSERT((NodeAlloc&)*this == (NodeAlloc&)x);
|
||||||
this->icont().splice(p.get(), x.icont(), first.get(), last.get());
|
this->icont().splice(p.get(), x.icont(), first.get(), last.get());
|
||||||
}
|
|
||||||
else{
|
|
||||||
throw std::runtime_error("list::splice called with unequal allocators");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Requires</b>: p must point to an element contained
|
//! <b>Requires</b>: p must point to an element contained
|
||||||
@@ -996,14 +998,10 @@ class list
|
|||||||
//!
|
//!
|
||||||
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
|
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
|
||||||
//! list. Iterators of this list and all the references are not invalidated.
|
//! list. Iterators of this list and all the references are not invalidated.
|
||||||
void splice(const_iterator p, ThisType &x, const_iterator first, const_iterator last, size_type n)
|
void splice(const_iterator p, ThisType &x, const_iterator first, const_iterator last, size_type n) BOOST_CONTAINER_NOEXCEPT
|
||||||
{
|
{
|
||||||
if((NodeAlloc&)*this == (NodeAlloc&)x){
|
BOOST_ASSERT((NodeAlloc&)*this == (NodeAlloc&)x);
|
||||||
this->icont().splice(p.get(), x.icont(), first.get(), last.get(), n);
|
this->icont().splice(p.get(), x.icont(), first.get(), last.get(), n);
|
||||||
}
|
|
||||||
else{
|
|
||||||
throw std::runtime_error("list::splice called with unequal allocators");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Reverses the order of elements in the list.
|
//! <b>Effects</b>: Reverses the order of elements in the list.
|
||||||
@@ -1240,11 +1238,11 @@ class list
|
|||||||
template <class InputIter>
|
template <class InputIter>
|
||||||
void priv_insert_dispatch(const_iterator p,
|
void priv_insert_dispatch(const_iterator p,
|
||||||
InputIter first, InputIter last,
|
InputIter first, InputIter last,
|
||||||
containers_detail::false_)
|
container_detail::false_)
|
||||||
{ this->priv_create_and_insert_nodes(p, first, last); }
|
{ this->priv_create_and_insert_nodes(p, first, last); }
|
||||||
|
|
||||||
template<class Integer>
|
template<class Integer>
|
||||||
void priv_insert_dispatch(const_iterator p, Integer n, Integer x, containers_detail::true_)
|
void priv_insert_dispatch(const_iterator p, Integer n, Integer x, container_detail::true_)
|
||||||
{ this->insert(p, (size_type)n, x); }
|
{ this->insert(p, (size_type)n, x); }
|
||||||
|
|
||||||
void priv_fill_assign(size_type n, const T& val)
|
void priv_fill_assign(size_type n, const T& val)
|
||||||
@@ -1262,11 +1260,11 @@ class list
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <class Integer>
|
template <class Integer>
|
||||||
void priv_assign_dispatch(Integer n, Integer val, containers_detail::true_)
|
void priv_assign_dispatch(Integer n, Integer val, container_detail::true_)
|
||||||
{ this->priv_fill_assign((size_type) n, (T) val); }
|
{ this->priv_fill_assign((size_type) n, (T) val); }
|
||||||
|
|
||||||
template <class InputIter>
|
template <class InputIter>
|
||||||
void priv_assign_dispatch(InputIter first2, InputIter last2, containers_detail::false_)
|
void priv_assign_dispatch(InputIter first2, InputIter last2, container_detail::false_)
|
||||||
{
|
{
|
||||||
iterator first1 = this->begin();
|
iterator first1 = this->begin();
|
||||||
iterator last1 = this->end();
|
iterator last1 = this->end();
|
||||||
@@ -1370,4 +1368,4 @@ namespace container {
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif // BOOST_CONTAINERS_LIST_HPP_
|
#endif // BOOST_CONTAINER_LIST_HPP_
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_MAP_HPP
|
#ifndef BOOST_CONTAINER_MAP_HPP
|
||||||
#define BOOST_CONTAINERS_MAP_HPP
|
#define BOOST_CONTAINER_MAP_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -31,7 +31,10 @@
|
|||||||
#include <boost/container/detail/pair.hpp>
|
#include <boost/container/detail/pair.hpp>
|
||||||
#include <boost/container/detail/type_traits.hpp>
|
#include <boost/container/detail/type_traits.hpp>
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
|
#include <boost/move/move_helpers.hpp>
|
||||||
#include <boost/static_assert.hpp>
|
#include <boost/static_assert.hpp>
|
||||||
|
#include <boost/container/detail/value_init.hpp>
|
||||||
|
|
||||||
|
|
||||||
#ifdef BOOST_CONTAINER_DOXYGEN_INVOKED
|
#ifdef BOOST_CONTAINER_DOXYGEN_INVOKED
|
||||||
namespace boost {
|
namespace boost {
|
||||||
@@ -74,9 +77,9 @@ class map
|
|||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
BOOST_COPYABLE_AND_MOVABLE(map)
|
BOOST_COPYABLE_AND_MOVABLE(map)
|
||||||
typedef containers_detail::rbtree<Key,
|
typedef container_detail::rbtree<Key,
|
||||||
std::pair<const Key, T>,
|
std::pair<const Key, T>,
|
||||||
containers_detail::select1st< std::pair<const Key, T> >,
|
container_detail::select1st< std::pair<const Key, T> >,
|
||||||
Pred,
|
Pred,
|
||||||
A> tree_t;
|
A> tree_t;
|
||||||
tree_t m_tree; // red-black tree representing map
|
tree_t m_tree; // red-black tree representing map
|
||||||
@@ -103,7 +106,7 @@ class map
|
|||||||
typedef typename tree_t::allocator_type allocator_type;
|
typedef typename tree_t::allocator_type allocator_type;
|
||||||
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
||||||
typedef std::pair<key_type, mapped_type> nonconst_value_type;
|
typedef std::pair<key_type, mapped_type> nonconst_value_type;
|
||||||
typedef containers_detail::pair
|
typedef container_detail::pair
|
||||||
<key_type, mapped_type> nonconst_impl_value_type;
|
<key_type, mapped_type> nonconst_impl_value_type;
|
||||||
|
|
||||||
/// @cond
|
/// @cond
|
||||||
@@ -122,16 +125,26 @@ class map
|
|||||||
/// @endcond
|
/// @endcond
|
||||||
typedef value_compare_impl value_compare;
|
typedef value_compare_impl value_compare;
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Default constructs an empty map.
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
map()
|
||||||
|
: m_tree()
|
||||||
|
{
|
||||||
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs an empty map using the specified comparison object
|
//! <b>Effects</b>: Constructs an empty map using the specified comparison object
|
||||||
//! and allocator.
|
//! and allocator.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
explicit map(const Pred& comp = Pred(),
|
explicit map(const Pred& comp,
|
||||||
const allocator_type& a = allocator_type())
|
const allocator_type& a = allocator_type())
|
||||||
: m_tree(comp, a)
|
: m_tree(comp, a)
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs an empty map using the specified comparison object and
|
//! <b>Effects</b>: Constructs an empty map using the specified comparison object and
|
||||||
@@ -145,7 +158,7 @@ class map
|
|||||||
: m_tree(first, last, comp, a, true)
|
: m_tree(first, last, comp, a, true)
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs an empty map using the specified comparison object and
|
//! <b>Effects</b>: Constructs an empty map using the specified comparison object and
|
||||||
@@ -162,7 +175,7 @@ class map
|
|||||||
: m_tree(ordered_range, first, last, comp, a)
|
: m_tree(ordered_range, first, last, comp, a)
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Copy constructs a map.
|
//! <b>Effects</b>: Copy constructs a map.
|
||||||
@@ -172,7 +185,7 @@ class map
|
|||||||
: m_tree(x.m_tree)
|
: m_tree(x.m_tree)
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Move constructs a map. Constructs *this using x's resources.
|
//! <b>Effects</b>: Move constructs a map. Constructs *this using x's resources.
|
||||||
@@ -184,7 +197,7 @@ class map
|
|||||||
: m_tree(boost::move(x.m_tree))
|
: m_tree(boost::move(x.m_tree))
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Makes *this a copy of x.
|
//! <b>Effects</b>: Makes *this a copy of x.
|
||||||
@@ -318,24 +331,14 @@ class map
|
|||||||
size_type max_size() const
|
size_type max_size() const
|
||||||
{ return m_tree.max_size(); }
|
{ return m_tree.max_size(); }
|
||||||
|
|
||||||
|
#if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
//! Effects: If there is no key equivalent to x in the map, inserts
|
//! Effects: If there is no key equivalent to x in the map, inserts
|
||||||
//! value_type(x, T()) into the map.
|
//! value_type(x, T()) into the map.
|
||||||
//!
|
//!
|
||||||
//! Returns: A reference to the mapped_type corresponding to x in *this.
|
//! Returns: A reference to the mapped_type corresponding to x in *this.
|
||||||
//!
|
//!
|
||||||
//! Complexity: Logarithmic.
|
//! Complexity: Logarithmic.
|
||||||
T& operator[](const key_type& k)
|
mapped_type& operator[](const key_type &k);
|
||||||
{
|
|
||||||
//we can optimize this
|
|
||||||
iterator i = lower_bound(k);
|
|
||||||
// i->first is greater than or equivalent to k.
|
|
||||||
if (i == end() || key_comp()(k, (*i).first)){
|
|
||||||
containers_detail::value_init<T> v;
|
|
||||||
value_type val(k, boost::move(v.m_t));
|
|
||||||
i = insert(i, boost::move(val));
|
|
||||||
}
|
|
||||||
return (*i).second;
|
|
||||||
}
|
|
||||||
|
|
||||||
//! Effects: If there is no key equivalent to x in the map, inserts
|
//! Effects: If there is no key equivalent to x in the map, inserts
|
||||||
//! value_type(boost::move(x), T()) into the map (the key is move-constructed)
|
//! value_type(boost::move(x), T()) into the map (the key is move-constructed)
|
||||||
@@ -343,18 +346,10 @@ class map
|
|||||||
//! Returns: A reference to the mapped_type corresponding to x in *this.
|
//! Returns: A reference to the mapped_type corresponding to x in *this.
|
||||||
//!
|
//!
|
||||||
//! Complexity: Logarithmic.
|
//! Complexity: Logarithmic.
|
||||||
T& operator[](BOOST_RV_REF(key_type) mk)
|
mapped_type& operator[](key_type &&k);
|
||||||
{
|
#else
|
||||||
key_type &k = mk;
|
BOOST_MOVE_CONVERSION_AWARE_CATCH( operator[] , key_type, mapped_type&, priv_subscript)
|
||||||
//we can optimize this
|
#endif
|
||||||
iterator i = lower_bound(k);
|
|
||||||
// i->first is greater than or equivalent to k.
|
|
||||||
if (i == end() || key_comp()(k, (*i).first)){
|
|
||||||
value_type val(boost::move(k), boost::move(T()));
|
|
||||||
i = insert(i, boost::move(val));
|
|
||||||
}
|
|
||||||
return (*i).second;
|
|
||||||
}
|
|
||||||
|
|
||||||
//! Returns: A reference to the element whose key is equivalent to x.
|
//! Returns: A reference to the element whose key is equivalent to x.
|
||||||
//! Throws: An exception object of type out_of_range if no such element is present.
|
//! Throws: An exception object of type out_of_range if no such element is present.
|
||||||
@@ -381,7 +376,6 @@ class map
|
|||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type() allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -508,7 +502,7 @@ class map
|
|||||||
void insert(InputIterator first, InputIterator last)
|
void insert(InputIterator first, InputIterator last)
|
||||||
{ m_tree.insert_unique(first, last); }
|
{ m_tree.insert_unique(first, last); }
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... in the container if and only if there is
|
//! std::forward<Args>(args)... in the container if and only if there is
|
||||||
@@ -538,27 +532,23 @@ class map
|
|||||||
iterator emplace_hint(const_iterator hint, Args&&... args)
|
iterator emplace_hint(const_iterator hint, Args&&... args)
|
||||||
{ return m_tree.emplace_hint_unique(hint, boost::forward<Args>(args)...); }
|
{ return m_tree.emplace_hint_unique(hint, boost::forward<Args>(args)...); }
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator emplace()
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
{ return m_tree.emplace_unique(); }
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace_hint(const_iterator hint)
|
{ return m_tree.emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
{ return m_tree.emplace_hint_unique(hint); }
|
\
|
||||||
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
iterator emplace_hint(const_iterator hint \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
{ return m_tree.emplace_hint_unique(hint \
|
||||||
{ return m_tree.emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); } \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _));} \
|
||||||
\
|
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
iterator emplace_hint(const_iterator hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
{ return m_tree.emplace_hint_unique(hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _));}\
|
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases the element pointed to by position.
|
//! <b>Effects</b>: Erases the element pointed to by position.
|
||||||
//!
|
//!
|
||||||
@@ -660,7 +650,35 @@ class map
|
|||||||
const map<K1, T1, C1, A1>&);
|
const map<K1, T1, C1, A1>&);
|
||||||
template <class K1, class T1, class C1, class A1>
|
template <class K1, class T1, class C1, class A1>
|
||||||
friend bool operator< (const map<K1, T1, C1, A1>&,
|
friend bool operator< (const map<K1, T1, C1, A1>&,
|
||||||
const map<K1, T1, C1, A1>&);
|
const map<K1, T1, C1, A1>&);
|
||||||
|
private:
|
||||||
|
mapped_type& priv_subscript(const key_type &k)
|
||||||
|
{
|
||||||
|
//we can optimize this
|
||||||
|
iterator i = lower_bound(k);
|
||||||
|
// i->first is greater than or equivalent to k.
|
||||||
|
if (i == end() || key_comp()(k, (*i).first)){
|
||||||
|
container_detail::value_init<mapped_type> m;
|
||||||
|
nonconst_impl_value_type val(k, boost::move(m.m_t));
|
||||||
|
i = insert(i, boost::move(val));
|
||||||
|
}
|
||||||
|
return (*i).second;
|
||||||
|
}
|
||||||
|
|
||||||
|
mapped_type& priv_subscript(BOOST_RV_REF(key_type) mk)
|
||||||
|
{
|
||||||
|
key_type &k = mk;
|
||||||
|
//we can optimize this
|
||||||
|
iterator i = lower_bound(k);
|
||||||
|
// i->first is greater than or equivalent to k.
|
||||||
|
if (i == end() || key_comp()(k, (*i).first)){
|
||||||
|
container_detail::value_init<mapped_type> m;
|
||||||
|
nonconst_impl_value_type val(boost::move(k), boost::move(m.m_t));
|
||||||
|
i = insert(i, boost::move(val));
|
||||||
|
}
|
||||||
|
return (*i).second;
|
||||||
|
}
|
||||||
|
|
||||||
/// @endcond
|
/// @endcond
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -747,12 +765,14 @@ class multimap
|
|||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
BOOST_COPYABLE_AND_MOVABLE(multimap)
|
BOOST_COPYABLE_AND_MOVABLE(multimap)
|
||||||
typedef containers_detail::rbtree<Key,
|
typedef container_detail::rbtree<Key,
|
||||||
std::pair<const Key, T>,
|
std::pair<const Key, T>,
|
||||||
containers_detail::select1st< std::pair<const Key, T> >,
|
container_detail::select1st< std::pair<const Key, T> >,
|
||||||
Pred,
|
Pred,
|
||||||
A> tree_t;
|
A> tree_t;
|
||||||
tree_t m_tree; // red-black tree representing map
|
tree_t m_tree; // red-black tree representing map
|
||||||
|
typedef typename container_detail::
|
||||||
|
move_const_ref_type<Key>::type insert_key_const_ref_type;
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
public:
|
public:
|
||||||
@@ -775,7 +795,7 @@ class multimap
|
|||||||
typedef typename tree_t::allocator_type allocator_type;
|
typedef typename tree_t::allocator_type allocator_type;
|
||||||
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
||||||
typedef std::pair<key_type, mapped_type> nonconst_value_type;
|
typedef std::pair<key_type, mapped_type> nonconst_value_type;
|
||||||
typedef containers_detail::pair
|
typedef container_detail::pair
|
||||||
<key_type, mapped_type> nonconst_impl_value_type;
|
<key_type, mapped_type> nonconst_impl_value_type;
|
||||||
|
|
||||||
/// @cond
|
/// @cond
|
||||||
@@ -794,16 +814,25 @@ class multimap
|
|||||||
/// @endcond
|
/// @endcond
|
||||||
typedef value_compare_impl value_compare;
|
typedef value_compare_impl value_compare;
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Default constructs an empty multimap.
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
multimap()
|
||||||
|
: m_tree()
|
||||||
|
{
|
||||||
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs an empty multimap using the specified comparison
|
//! <b>Effects</b>: Constructs an empty multimap using the specified comparison
|
||||||
//! object and allocator.
|
//! object and allocator.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
explicit multimap(const Pred& comp = Pred(),
|
explicit multimap(const Pred& comp, const allocator_type& a = allocator_type())
|
||||||
const allocator_type& a = allocator_type())
|
|
||||||
: m_tree(comp, a)
|
: m_tree(comp, a)
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs an empty multimap using the specified comparison object
|
//! <b>Effects</b>: Constructs an empty multimap using the specified comparison object
|
||||||
@@ -818,7 +847,7 @@ class multimap
|
|||||||
: m_tree(first, last, comp, a, false)
|
: m_tree(first, last, comp, a, false)
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs an empty multimap using the specified comparison object and
|
//! <b>Effects</b>: Constructs an empty multimap using the specified comparison object and
|
||||||
@@ -842,7 +871,7 @@ class multimap
|
|||||||
: m_tree(x.m_tree)
|
: m_tree(x.m_tree)
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Move constructs a multimap. Constructs *this using x's resources.
|
//! <b>Effects</b>: Move constructs a multimap. Constructs *this using x's resources.
|
||||||
@@ -854,7 +883,7 @@ class multimap
|
|||||||
: m_tree(boost::move(x.m_tree))
|
: m_tree(boost::move(x.m_tree))
|
||||||
{
|
{
|
||||||
//Allocator type must be std::pair<CONST Key, T>
|
//Allocator type must be std::pair<CONST Key, T>
|
||||||
BOOST_STATIC_ASSERT((containers_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
BOOST_STATIC_ASSERT((container_detail::is_same<std::pair<const Key, T>, typename A::value_type>::value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Makes *this a copy of x.
|
//! <b>Effects</b>: Makes *this a copy of x.
|
||||||
@@ -989,7 +1018,6 @@ class multimap
|
|||||||
{ return m_tree.max_size(); }
|
{ return m_tree.max_size(); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type() allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -1078,7 +1106,7 @@ class multimap
|
|||||||
void insert(InputIterator first, InputIterator last)
|
void insert(InputIterator first, InputIterator last)
|
||||||
{ m_tree.insert_equal(first, last); }
|
{ m_tree.insert_equal(first, last); }
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... in the container.
|
//! std::forward<Args>(args)... in the container.
|
||||||
@@ -1106,27 +1134,23 @@ class multimap
|
|||||||
iterator emplace_hint(const_iterator hint, Args&&... args)
|
iterator emplace_hint(const_iterator hint, Args&&... args)
|
||||||
{ return m_tree.emplace_hint_equal(hint, boost::forward<Args>(args)...); }
|
{ return m_tree.emplace_hint_equal(hint, boost::forward<Args>(args)...); }
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator emplace()
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
{ return m_tree.emplace_equal(); }
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace_hint(const_iterator hint)
|
{ return m_tree.emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
{ return m_tree.emplace_hint_equal(hint); }
|
\
|
||||||
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
iterator emplace_hint(const_iterator hint \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
{ return m_tree.emplace_hint_equal(hint \
|
||||||
{ return m_tree.emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); } \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _));} \
|
||||||
\
|
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
iterator emplace_hint(const_iterator hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
{ return m_tree.emplace_hint_equal(hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); }\
|
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases the element pointed to by position.
|
//! <b>Effects</b>: Erases the element pointed to by position.
|
||||||
//!
|
//!
|
||||||
@@ -1288,5 +1312,5 @@ namespace container {
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif /* BOOST_CONTAINERS_MAP_HPP */
|
#endif /* BOOST_CONTAINER_MAP_HPP */
|
||||||
|
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_SET_HPP
|
#ifndef BOOST_CONTAINER_SET_HPP
|
||||||
#define BOOST_CONTAINERS_SET_HPP
|
#define BOOST_CONTAINER_SET_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -27,7 +27,7 @@
|
|||||||
#include <boost/container/detail/mpl.hpp>
|
#include <boost/container/detail/mpl.hpp>
|
||||||
#include <boost/container/detail/tree.hpp>
|
#include <boost/container/detail/tree.hpp>
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
#ifndef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#ifndef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
#include <boost/container/detail/preprocessor.hpp>
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -67,10 +67,10 @@ class set
|
|||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
BOOST_COPYABLE_AND_MOVABLE(set)
|
BOOST_COPYABLE_AND_MOVABLE(set)
|
||||||
typedef containers_detail::rbtree<T, T,
|
typedef container_detail::rbtree<T, T,
|
||||||
containers_detail::identity<T>, Pred, A> tree_t;
|
container_detail::identity<T>, Pred, A> tree_t;
|
||||||
tree_t m_tree; // red-black tree representing set
|
tree_t m_tree; // red-black tree representing set
|
||||||
typedef typename containers_detail::
|
typedef typename container_detail::
|
||||||
move_const_ref_type<T>::type insert_const_ref_type;
|
move_const_ref_type<T>::type insert_const_ref_type;
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
@@ -94,11 +94,18 @@ class set
|
|||||||
typedef typename tree_t::allocator_type allocator_type;
|
typedef typename tree_t::allocator_type allocator_type;
|
||||||
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
typedef typename tree_t::stored_allocator_type stored_allocator_type;
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Default constructs an empty set.
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
set()
|
||||||
|
: m_tree()
|
||||||
|
{}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs an empty set using the specified comparison object
|
//! <b>Effects</b>: Constructs an empty set using the specified comparison object
|
||||||
//! and allocator.
|
//! and allocator.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
explicit set(const Pred& comp = Pred(),
|
explicit set(const Pred& comp,
|
||||||
const allocator_type& a = allocator_type())
|
const allocator_type& a = allocator_type())
|
||||||
: m_tree(comp, a)
|
: m_tree(comp, a)
|
||||||
{}
|
{}
|
||||||
@@ -310,7 +317,6 @@ class set
|
|||||||
{ return m_tree.max_size(); }
|
{ return m_tree.max_size(); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type() allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -334,7 +340,7 @@ class set
|
|||||||
{ return this->insert(const_cast<const T &>(x)); }
|
{ return this->insert(const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
std::pair<iterator,bool> insert(const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
std::pair<iterator,bool> insert(const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_insert(u); }
|
{ return priv_insert(u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -366,7 +372,7 @@ class set
|
|||||||
{ return this->insert(position, const_cast<const T &>(x)); }
|
{ return this->insert(position, const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert(const_iterator position, const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert(const_iterator position, const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_insert(position, u); }
|
{ return priv_insert(position, u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -389,7 +395,7 @@ class set
|
|||||||
void insert(InputIterator first, InputIterator last)
|
void insert(InputIterator first, InputIterator last)
|
||||||
{ m_tree.insert_unique(first, last); }
|
{ m_tree.insert_unique(first, last); }
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... if and only if there is
|
//! std::forward<Args>(args)... if and only if there is
|
||||||
@@ -418,27 +424,23 @@ class set
|
|||||||
iterator emplace_hint(const_iterator hint, Args&&... args)
|
iterator emplace_hint(const_iterator hint, Args&&... args)
|
||||||
{ return m_tree.emplace_hint_unique(hint, boost::forward<Args>(args)...); }
|
{ return m_tree.emplace_hint_unique(hint, boost::forward<Args>(args)...); }
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator emplace()
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
{ return m_tree.emplace_unique(); }
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace_hint(const_iterator hint)
|
{ return m_tree.emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
{ return m_tree.emplace_hint_unique(hint); }
|
\
|
||||||
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
iterator emplace_hint(const_iterator hint \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
{ return m_tree.emplace_hint_unique(hint \
|
||||||
{ return m_tree.emplace_unique(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); } \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _));} \
|
||||||
\
|
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
iterator emplace_hint(const_iterator hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
{ return m_tree.emplace_hint_unique(hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _));}\
|
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases the element pointed to by p.
|
//! <b>Effects</b>: Erases the element pointed to by p.
|
||||||
//!
|
//!
|
||||||
@@ -629,10 +631,10 @@ class multiset
|
|||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
BOOST_COPYABLE_AND_MOVABLE(multiset)
|
BOOST_COPYABLE_AND_MOVABLE(multiset)
|
||||||
typedef containers_detail::rbtree<T, T,
|
typedef container_detail::rbtree<T, T,
|
||||||
containers_detail::identity<T>, Pred, A> tree_t;
|
container_detail::identity<T>, Pred, A> tree_t;
|
||||||
tree_t m_tree; // red-black tree representing multiset
|
tree_t m_tree; // red-black tree representing multiset
|
||||||
typedef typename containers_detail::
|
typedef typename container_detail::
|
||||||
move_const_ref_type<T>::type insert_const_ref_type;
|
move_const_ref_type<T>::type insert_const_ref_type;
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
@@ -660,7 +662,15 @@ class multiset
|
|||||||
//! object and allocator.
|
//! object and allocator.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
explicit multiset(const Pred& comp = Pred(),
|
multiset()
|
||||||
|
: m_tree()
|
||||||
|
{}
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Constructs an empty multiset using the specified comparison
|
||||||
|
//! object and allocator.
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
explicit multiset(const Pred& comp,
|
||||||
const allocator_type& a = allocator_type())
|
const allocator_type& a = allocator_type())
|
||||||
: m_tree(comp, a)
|
: m_tree(comp, a)
|
||||||
{}
|
{}
|
||||||
@@ -873,7 +883,6 @@ class multiset
|
|||||||
{ return m_tree.max_size(); }
|
{ return m_tree.max_size(); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type() allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -893,7 +902,7 @@ class multiset
|
|||||||
{ return this->insert(const_cast<const T &>(x)); }
|
{ return this->insert(const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert(const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert(const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_insert(u); }
|
{ return priv_insert(u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -923,7 +932,7 @@ class multiset
|
|||||||
{ return this->insert(position, const_cast<const T &>(x)); }
|
{ return this->insert(position, const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert(const_iterator position, const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert(const_iterator position, const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_insert(position, u); }
|
{ return priv_insert(position, u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -947,7 +956,7 @@ class multiset
|
|||||||
void insert(InputIterator first, InputIterator last)
|
void insert(InputIterator first, InputIterator last)
|
||||||
{ m_tree.insert_equal(first, last); }
|
{ m_tree.insert_equal(first, last); }
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... and returns the iterator pointing to the
|
//! std::forward<Args>(args)... and returns the iterator pointing to the
|
||||||
@@ -970,27 +979,23 @@ class multiset
|
|||||||
iterator emplace_hint(const_iterator hint, Args&&... args)
|
iterator emplace_hint(const_iterator hint, Args&&... args)
|
||||||
{ return m_tree.emplace_hint_equal(hint, boost::forward<Args>(args)...); }
|
{ return m_tree.emplace_hint_equal(hint, boost::forward<Args>(args)...); }
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
iterator emplace()
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
{ return m_tree.emplace_equal(); }
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace_hint(const_iterator hint)
|
{ return m_tree.emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); } \
|
||||||
{ return m_tree.emplace_hint_equal(hint); }
|
\
|
||||||
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
iterator emplace_hint(const_iterator hint \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
iterator emplace(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
{ return m_tree.emplace_hint_equal(hint \
|
||||||
{ return m_tree.emplace_equal(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); } \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _));} \
|
||||||
\
|
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
iterator emplace_hint(const_iterator hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
{ return m_tree.emplace_hint_equal(hint, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); }\
|
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases the element pointed to by p.
|
//! <b>Effects</b>: Erases the element pointed to by p.
|
||||||
//!
|
//!
|
||||||
@@ -1159,5 +1164,5 @@ namespace container {
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif /* BOOST_CONTAINERS_SET_HPP */
|
#endif /* BOOST_CONTAINER_SET_HPP */
|
||||||
|
|
||||||
|
@@ -8,8 +8,8 @@
|
|||||||
//
|
//
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_SLIST_HPP
|
#ifndef BOOST_CONTAINER_SLIST_HPP
|
||||||
#define BOOST_CONTAINERS_SLIST_HPP
|
#define BOOST_CONTAINER_SLIST_HPP
|
||||||
|
|
||||||
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
|
||||||
# pragma once
|
# pragma once
|
||||||
@@ -20,7 +20,7 @@
|
|||||||
|
|
||||||
#include <boost/container/container_fwd.hpp>
|
#include <boost/container/container_fwd.hpp>
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
#include <boost/pointer_to_other.hpp>
|
#include <boost/intrusive/pointer_traits.hpp>
|
||||||
#include <boost/container/detail/utilities.hpp>
|
#include <boost/container/detail/utilities.hpp>
|
||||||
#include <boost/container/detail/mpl.hpp>
|
#include <boost/container/detail/mpl.hpp>
|
||||||
#include <boost/type_traits/has_trivial_destructor.hpp>
|
#include <boost/type_traits/has_trivial_destructor.hpp>
|
||||||
@@ -29,7 +29,7 @@
|
|||||||
#include <boost/intrusive/slist.hpp>
|
#include <boost/intrusive/slist.hpp>
|
||||||
|
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
//Preprocessor library to emulate perfect forwarding
|
//Preprocessor library to emulate perfect forwarding
|
||||||
#else
|
#else
|
||||||
#include <boost/container/detail/preprocessor.hpp>
|
#include <boost/container/detail/preprocessor.hpp>
|
||||||
@@ -52,46 +52,43 @@ namespace container {
|
|||||||
|
|
||||||
/// @cond
|
/// @cond
|
||||||
|
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template<class VoidPointer>
|
template<class VoidPointer>
|
||||||
struct slist_hook
|
struct slist_hook
|
||||||
{
|
{
|
||||||
typedef typename containers_detail::bi::make_slist_base_hook
|
typedef typename container_detail::bi::make_slist_base_hook
|
||||||
<containers_detail::bi::void_pointer<VoidPointer>, containers_detail::bi::link_mode<containers_detail::bi::normal_link> >::type type;
|
<container_detail::bi::void_pointer<VoidPointer>, container_detail::bi::link_mode<container_detail::bi::normal_link> >::type type;
|
||||||
};
|
};
|
||||||
|
|
||||||
template <class T, class VoidPointer>
|
template <class T, class VoidPointer>
|
||||||
struct slist_node
|
struct slist_node
|
||||||
: public slist_hook<VoidPointer>::type
|
: public slist_hook<VoidPointer>::type
|
||||||
{
|
{
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
|
||||||
|
|
||||||
slist_node()
|
slist_node()
|
||||||
: m_data()
|
: m_data()
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
template<class ...Args>
|
template<class ...Args>
|
||||||
slist_node(Args &&...args)
|
slist_node(Args &&...args)
|
||||||
: m_data(boost::forward<Args>(args)...)
|
: m_data(boost::forward<Args>(args)...)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
slist_node()
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
: m_data()
|
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
||||||
{}
|
slist_node(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
|
: m_data(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)) \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
{} \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
slist_node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
: m_data(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)) \
|
|
||||||
{} \
|
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif//#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif//#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
T m_data;
|
T m_data;
|
||||||
};
|
};
|
||||||
@@ -99,22 +96,26 @@ struct slist_node
|
|||||||
template<class A>
|
template<class A>
|
||||||
struct intrusive_slist_type
|
struct intrusive_slist_type
|
||||||
{
|
{
|
||||||
typedef typename A::value_type value_type;
|
typedef boost::container::allocator_traits<A> allocator_traits_type;
|
||||||
typedef typename boost::pointer_to_other
|
typedef typename allocator_traits_type::value_type value_type;
|
||||||
<typename A::pointer, void>::type void_pointer;
|
typedef typename boost::intrusive::pointer_traits
|
||||||
typedef typename containers_detail::slist_node
|
<typename allocator_traits_type::pointer>::template
|
||||||
|
rebind_pointer<void>::type
|
||||||
|
void_pointer;
|
||||||
|
typedef typename container_detail::slist_node
|
||||||
<value_type, void_pointer> node_type;
|
<value_type, void_pointer> node_type;
|
||||||
|
|
||||||
typedef typename containers_detail::bi::make_slist
|
typedef typename container_detail::bi::make_slist
|
||||||
<node_type
|
<node_type
|
||||||
,containers_detail::bi::base_hook<typename slist_hook<void_pointer>::type>
|
,container_detail::bi::base_hook<typename slist_hook<void_pointer>::type>
|
||||||
,containers_detail::bi::constant_time_size<true>
|
,container_detail::bi::constant_time_size<true>
|
||||||
,containers_detail::bi::size_type<typename A::size_type>
|
, container_detail::bi::size_type
|
||||||
|
<typename allocator_traits_type::size_type>
|
||||||
>::type container_type;
|
>::type container_type;
|
||||||
typedef container_type type ;
|
typedef container_type type ;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
|
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
@@ -156,24 +157,25 @@ template <class T, class A = std::allocator<T> >
|
|||||||
template <class T, class A>
|
template <class T, class A>
|
||||||
#endif
|
#endif
|
||||||
class slist
|
class slist
|
||||||
: protected containers_detail::node_alloc_holder
|
: protected container_detail::node_alloc_holder
|
||||||
<A, typename containers_detail::intrusive_slist_type<A>::type>
|
<A, typename container_detail::intrusive_slist_type<A>::type>
|
||||||
{
|
{
|
||||||
/// @cond
|
/// @cond
|
||||||
typedef typename containers_detail::
|
typedef typename container_detail::
|
||||||
move_const_ref_type<T>::type insert_const_ref_type;
|
move_const_ref_type<T>::type insert_const_ref_type;
|
||||||
typedef typename
|
typedef typename
|
||||||
containers_detail::intrusive_slist_type<A>::type Icont;
|
container_detail::intrusive_slist_type<A>::type Icont;
|
||||||
typedef containers_detail::node_alloc_holder<A, Icont> AllocHolder;
|
typedef container_detail::node_alloc_holder<A, Icont> AllocHolder;
|
||||||
typedef typename AllocHolder::NodePtr NodePtr;
|
typedef typename AllocHolder::NodePtr NodePtr;
|
||||||
typedef slist <T, A> ThisType;
|
typedef slist <T, A> ThisType;
|
||||||
typedef typename AllocHolder::NodeAlloc NodeAlloc;
|
typedef typename AllocHolder::NodeAlloc NodeAlloc;
|
||||||
typedef typename AllocHolder::ValAlloc ValAlloc;
|
typedef typename AllocHolder::ValAlloc ValAlloc;
|
||||||
typedef typename AllocHolder::Node Node;
|
typedef typename AllocHolder::Node Node;
|
||||||
typedef containers_detail::allocator_destroyer<NodeAlloc> Destroyer;
|
typedef container_detail::allocator_destroyer<NodeAlloc> Destroyer;
|
||||||
typedef typename AllocHolder::allocator_v1 allocator_v1;
|
typedef typename AllocHolder::allocator_v1 allocator_v1;
|
||||||
typedef typename AllocHolder::allocator_v2 allocator_v2;
|
typedef typename AllocHolder::allocator_v2 allocator_v2;
|
||||||
typedef typename AllocHolder::alloc_version alloc_version;
|
typedef typename AllocHolder::alloc_version alloc_version;
|
||||||
|
typedef boost::container::allocator_traits<A> allocator_traits_type;
|
||||||
|
|
||||||
class equal_to_value
|
class equal_to_value
|
||||||
{
|
{
|
||||||
@@ -206,23 +208,23 @@ class slist
|
|||||||
/// @endcond
|
/// @endcond
|
||||||
public:
|
public:
|
||||||
//! The type of object, T, stored in the list
|
//! The type of object, T, stored in the list
|
||||||
typedef T value_type;
|
typedef T value_type;
|
||||||
//! Pointer to T
|
//! Pointer to T
|
||||||
typedef typename A::pointer pointer;
|
typedef typename allocator_traits_type::pointer pointer;
|
||||||
//! Const pointer to T
|
//! Const pointer to T
|
||||||
typedef typename A::const_pointer const_pointer;
|
typedef typename allocator_traits_type::const_pointer const_pointer;
|
||||||
//! Reference to T
|
//! Reference to T
|
||||||
typedef typename A::reference reference;
|
typedef typename allocator_traits_type::reference reference;
|
||||||
//! Const reference to T
|
//! Const reference to T
|
||||||
typedef typename A::const_reference const_reference;
|
typedef typename allocator_traits_type::const_reference const_reference;
|
||||||
//! An unsigned integral type
|
//! An unsigned integral type
|
||||||
typedef typename A::size_type size_type;
|
typedef typename allocator_traits_type::size_type size_type;
|
||||||
//! A signed integral type
|
//! A signed integral type
|
||||||
typedef typename A::difference_type difference_type;
|
typedef typename allocator_traits_type::difference_type difference_type;
|
||||||
//! The allocator type
|
//! The allocator type
|
||||||
typedef A allocator_type;
|
typedef A allocator_type;
|
||||||
//! The stored allocator type
|
//! Non-standard extension: the stored allocator type
|
||||||
typedef NodeAlloc stored_allocator_type;
|
typedef NodeAlloc stored_allocator_type;
|
||||||
|
|
||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
@@ -328,7 +330,16 @@ class slist
|
|||||||
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
explicit slist(const allocator_type& a = allocator_type())
|
slist()
|
||||||
|
: AllocHolder()
|
||||||
|
{}
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Constructs a list taking the allocator as parameter.
|
||||||
|
//!
|
||||||
|
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
explicit slist(const allocator_type& a)
|
||||||
: AllocHolder(a)
|
: AllocHolder(a)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
@@ -377,7 +388,7 @@ class slist
|
|||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
slist(BOOST_RV_REF(slist) x)
|
slist(BOOST_RV_REF(slist) x)
|
||||||
: AllocHolder(boost::move((AllocHolder&)x))
|
: AllocHolder(boost::move(static_cast<AllocHolder&>(x)))
|
||||||
{}
|
{}
|
||||||
|
|
||||||
//! <b>Effects</b>: Makes *this contain the same elements as x.
|
//! <b>Effects</b>: Makes *this contain the same elements as x.
|
||||||
@@ -391,6 +402,14 @@ class slist
|
|||||||
slist& operator= (BOOST_COPY_ASSIGN_REF(slist) x)
|
slist& operator= (BOOST_COPY_ASSIGN_REF(slist) x)
|
||||||
{
|
{
|
||||||
if (&x != this){
|
if (&x != this){
|
||||||
|
NodeAlloc &this_alloc = this->node_alloc();
|
||||||
|
const NodeAlloc &x_alloc = x.node_alloc();
|
||||||
|
container_detail::bool_<allocator_traits_type::
|
||||||
|
propagate_on_container_copy_assignment::value> flag;
|
||||||
|
if(flag && this_alloc != x_alloc){
|
||||||
|
this->clear();
|
||||||
|
}
|
||||||
|
this->AllocHolder::copy_assign_alloc(x);
|
||||||
this->assign(x.begin(), x.end());
|
this->assign(x.begin(), x.end());
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
@@ -404,11 +423,25 @@ class slist
|
|||||||
//! <b>Throws</b>: If memory allocation throws or T's copy constructor throws.
|
//! <b>Throws</b>: If memory allocation throws or T's copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Linear to the number of elements in x.
|
//! <b>Complexity</b>: Linear to the number of elements in x.
|
||||||
slist& operator= (BOOST_RV_REF(slist) mx)
|
slist& operator= (BOOST_RV_REF(slist) x)
|
||||||
{
|
{
|
||||||
if (&mx != this){
|
if (&x != this){
|
||||||
this->clear();
|
NodeAlloc &this_alloc = this->node_alloc();
|
||||||
this->swap(mx);
|
NodeAlloc &x_alloc = x.node_alloc();
|
||||||
|
//If allocators a re equal we can just swap pointers
|
||||||
|
if(this_alloc == x_alloc){
|
||||||
|
//Destroy and swap pointers
|
||||||
|
this->clear();
|
||||||
|
this->icont() = boost::move(x.icont());
|
||||||
|
//Move allocator if needed
|
||||||
|
this->AllocHolder::move_assign_alloc(x);
|
||||||
|
}
|
||||||
|
//If unequal allocators, then do a one by one move
|
||||||
|
else{
|
||||||
|
typedef typename std::iterator_traits<iterator>::iterator_category ItCat;
|
||||||
|
this->assign( boost::make_move_iterator(x.begin())
|
||||||
|
, boost::make_move_iterator(x.end()));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
@@ -455,8 +488,8 @@ class slist
|
|||||||
template <class InpIt>
|
template <class InpIt>
|
||||||
void assign(InpIt first, InpIt last)
|
void assign(InpIt first, InpIt last)
|
||||||
{
|
{
|
||||||
const bool aux_boolean = containers_detail::is_convertible<InpIt, size_type>::value;
|
const bool aux_boolean = container_detail::is_convertible<InpIt, size_type>::value;
|
||||||
typedef containers_detail::bool_<aux_boolean> Result;
|
typedef container_detail::bool_<aux_boolean> Result;
|
||||||
this->priv_assign_dispatch(first, last, Result());
|
this->priv_assign_dispatch(first, last, Result());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -563,8 +596,6 @@ class slist
|
|||||||
{ return !this->size(); }
|
{ return !this->size(); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type()
|
|
||||||
//! allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -607,7 +638,7 @@ class slist
|
|||||||
void push_front(T &x) { push_front(const_cast<const T &>(x)); }
|
void push_front(T &x) { push_front(const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
void push_front(const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
void push_front(const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_push_front(u); }
|
{ return priv_push_front(u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -669,7 +700,7 @@ class slist
|
|||||||
{ return this->insert_after(position, const_cast<const T &>(x)); }
|
{ return this->insert_after(position, const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert_after(const_iterator position, const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert_after(const_iterator position, const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return this->priv_insert_after(position, u); }
|
{ return this->priv_insert_after(position, u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -717,8 +748,8 @@ class slist
|
|||||||
template <class InIter>
|
template <class InIter>
|
||||||
void insert_after(const_iterator prev_pos, InIter first, InIter last)
|
void insert_after(const_iterator prev_pos, InIter first, InIter last)
|
||||||
{
|
{
|
||||||
const bool aux_boolean = containers_detail::is_convertible<InIter, size_type>::value;
|
const bool aux_boolean = container_detail::is_convertible<InIter, size_type>::value;
|
||||||
typedef containers_detail::bool_<aux_boolean> Result;
|
typedef container_detail::bool_<aux_boolean> Result;
|
||||||
this->priv_insert_after_range_dispatch(prev_pos, first, last, Result());
|
this->priv_insert_after_range_dispatch(prev_pos, first, last, Result());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -737,7 +768,7 @@ class slist
|
|||||||
{ return this->insert(position, const_cast<const T &>(x)); }
|
{ return this->insert(position, const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert(const_iterator position, const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert(const_iterator position, const U &u, typename container_detail::enable_if_c<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return this->priv_insert(position, u); }
|
{ return this->priv_insert(position, u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -774,7 +805,7 @@ class slist
|
|||||||
void insert(const_iterator p, InIter first, InIter last)
|
void insert(const_iterator p, InIter first, InIter last)
|
||||||
{ return this->insert_after(previous(p), first, last); }
|
{ return this->insert_after(previous(p), first, last); }
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... in the front of the list
|
//! std::forward<Args>(args)... in the front of the list
|
||||||
@@ -808,63 +839,42 @@ class slist
|
|||||||
template <class... Args>
|
template <class... Args>
|
||||||
iterator emplace_after(const_iterator prev, Args&&... args)
|
iterator emplace_after(const_iterator prev, Args&&... args)
|
||||||
{
|
{
|
||||||
typename AllocHolder::Deallocator d(AllocHolder::create_node_and_deallocator());
|
NodePtr pnode(AllocHolder::create_node(boost::forward<Args>(args)...));
|
||||||
new ((void*)containers_detail::get_pointer(d.get())) Node(boost::forward<Args>(args)...);
|
return iterator(this->icont().insert_after(prev.get(), *pnode));
|
||||||
NodePtr node = d.get();
|
|
||||||
d.release();
|
|
||||||
return iterator(this->icont().insert_after(prev.get(), *node));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#else //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//0 args
|
|
||||||
void emplace_front()
|
|
||||||
{ this->emplace_after(this->cbefore_begin()); }
|
|
||||||
|
|
||||||
iterator emplace(const_iterator p)
|
|
||||||
{ return this->emplace_after(this->previous(p)); }
|
|
||||||
|
|
||||||
iterator emplace_after(const_iterator prev)
|
|
||||||
{
|
|
||||||
typename AllocHolder::Deallocator d(AllocHolder::create_node_and_deallocator());
|
|
||||||
new ((void*)containers_detail::get_pointer(d.get())) Node();
|
|
||||||
NodePtr node = d.get();
|
|
||||||
d.release();
|
|
||||||
return iterator(this->icont().insert_after(prev.get(), *node));
|
|
||||||
}
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
void emplace_front(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
void emplace_front(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
this->emplace \
|
this->emplace(this->cbegin() \
|
||||||
(this->cbegin(), BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace \
|
iterator emplace (const_iterator p \
|
||||||
(const_iterator p, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
return this->emplace_after \
|
return this->emplace_after \
|
||||||
(this->previous(p), BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
(this->previous(p) \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)); \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace_after \
|
iterator emplace_after(const_iterator prev \
|
||||||
(const_iterator prev, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
typename AllocHolder::Deallocator d(AllocHolder::create_node_and_deallocator()); \
|
NodePtr pnode (AllocHolder::create_node \
|
||||||
new ((void*)containers_detail::get_pointer(d.get())) \
|
(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _))); \
|
||||||
Node(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
return iterator(this->icont().insert_after(prev.get(), *pnode)); \
|
||||||
NodePtr node = d.get(); \
|
|
||||||
d.release(); \
|
|
||||||
return iterator(this->icont().insert_after(prev.get(), *node)); \
|
|
||||||
} \
|
} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases the element after the element pointed by prev_pos
|
//! <b>Effects</b>: Erases the element after the element pointed by prev_pos
|
||||||
//! of the list.
|
//! of the list.
|
||||||
@@ -1337,11 +1347,11 @@ class slist
|
|||||||
template <class InputIter>
|
template <class InputIter>
|
||||||
void priv_insert_dispatch(const_iterator prev,
|
void priv_insert_dispatch(const_iterator prev,
|
||||||
InputIter first, InputIter last,
|
InputIter first, InputIter last,
|
||||||
containers_detail::false_)
|
container_detail::false_)
|
||||||
{ this->priv_create_and_insert_nodes(prev, first, last); }
|
{ this->priv_create_and_insert_nodes(prev, first, last); }
|
||||||
|
|
||||||
template<class Integer>
|
template<class Integer>
|
||||||
void priv_insert_dispatch(const_iterator prev, Integer n, Integer x, containers_detail::true_)
|
void priv_insert_dispatch(const_iterator prev, Integer n, Integer x, container_detail::true_)
|
||||||
{ this->priv_create_and_insert_nodes(prev, (size_type)n, x); }
|
{ this->priv_create_and_insert_nodes(prev, (size_type)n, x); }
|
||||||
|
|
||||||
void priv_fill_assign(size_type n, const T& val)
|
void priv_fill_assign(size_type n, const T& val)
|
||||||
@@ -1361,11 +1371,11 @@ class slist
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <class Int>
|
template <class Int>
|
||||||
void priv_assign_dispatch(Int n, Int val, containers_detail::true_)
|
void priv_assign_dispatch(Int n, Int val, container_detail::true_)
|
||||||
{ this->priv_fill_assign((size_type) n, (T)val); }
|
{ this->priv_fill_assign((size_type) n, (T)val); }
|
||||||
|
|
||||||
template <class InpIt>
|
template <class InpIt>
|
||||||
void priv_assign_dispatch(InpIt first, InpIt last, containers_detail::false_)
|
void priv_assign_dispatch(InpIt first, InpIt last, container_detail::false_)
|
||||||
{
|
{
|
||||||
iterator end_n(this->end());
|
iterator end_n(this->end());
|
||||||
iterator prev(this->before_begin());
|
iterator prev(this->before_begin());
|
||||||
@@ -1383,11 +1393,11 @@ class slist
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <class Int>
|
template <class Int>
|
||||||
void priv_insert_after_range_dispatch(const_iterator prev_pos, Int n, Int x, containers_detail::true_)
|
void priv_insert_after_range_dispatch(const_iterator prev_pos, Int n, Int x, container_detail::true_)
|
||||||
{ this->priv_create_and_insert_nodes(prev_pos, (size_type)n, x); }
|
{ this->priv_create_and_insert_nodes(prev_pos, (size_type)n, x); }
|
||||||
|
|
||||||
template <class InIter>
|
template <class InIter>
|
||||||
void priv_insert_after_range_dispatch(const_iterator prev_pos, InIter first, InIter last, containers_detail::false_)
|
void priv_insert_after_range_dispatch(const_iterator prev_pos, InIter first, InIter last, container_detail::false_)
|
||||||
{ this->priv_create_and_insert_nodes(prev_pos, first, last); }
|
{ this->priv_create_and_insert_nodes(prev_pos, first, last); }
|
||||||
|
|
||||||
//Functors for member algorithm defaults
|
//Functors for member algorithm defaults
|
||||||
@@ -1533,4 +1543,4 @@ class insert_iterator<boost::container::slist<T, A> >
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif /* BOOST_CONTAINERS_SLIST_HPP */
|
#endif /* BOOST_CONTAINER_SLIST_HPP */
|
||||||
|
@@ -27,15 +27,14 @@
|
|||||||
#include <boost/container/container_fwd.hpp>
|
#include <boost/container/container_fwd.hpp>
|
||||||
#include <boost/mpl/bool.hpp>
|
#include <boost/mpl/bool.hpp>
|
||||||
#include <boost/mpl/not.hpp>
|
#include <boost/mpl/not.hpp>
|
||||||
#include <boost/noncopyable.hpp>
|
|
||||||
#include <boost/type_traits/is_integral.hpp>
|
#include <boost/type_traits/is_integral.hpp>
|
||||||
#include <boost/container/detail/version_type.hpp>
|
#include <boost/container/detail/version_type.hpp>
|
||||||
#include <boost/container/detail/multiallocation_chain.hpp>
|
#include <boost/container/detail/multiallocation_chain.hpp>
|
||||||
#include <boost/container/detail/utilities.hpp>
|
#include <boost/container/detail/utilities.hpp>
|
||||||
#include <boost/container/detail/iterators.hpp>
|
#include <boost/container/detail/iterators.hpp>
|
||||||
#include <boost/container/detail/algorithms.hpp>
|
#include <boost/container/detail/algorithms.hpp>
|
||||||
#include <boost/pointer_to_other.hpp>
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
#include <boost/get_pointer.hpp>
|
#include <boost/intrusive/pointer_traits.hpp>
|
||||||
|
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <stdexcept>
|
#include <stdexcept>
|
||||||
@@ -79,7 +78,7 @@ struct smart_ptr_type<T*>
|
|||||||
};
|
};
|
||||||
|
|
||||||
template<class Ptr>
|
template<class Ptr>
|
||||||
inline typename smart_ptr_type<Ptr>::pointer get_pointer(const Ptr &ptr)
|
inline typename smart_ptr_type<Ptr>::pointer to_raw_pointer(const Ptr &ptr)
|
||||||
{ return smart_ptr_type<Ptr>::get(ptr); }
|
{ return smart_ptr_type<Ptr>::get(ptr); }
|
||||||
|
|
||||||
template <class C>
|
template <class C>
|
||||||
@@ -126,33 +125,29 @@ template<typename VoidPointer, typename T>
|
|||||||
struct node_type
|
struct node_type
|
||||||
: public node_type_base<VoidPointer>
|
: public node_type_base<VoidPointer>
|
||||||
{
|
{
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
|
||||||
|
|
||||||
node_type()
|
node_type()
|
||||||
: value()
|
: value()
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
template<class ...Args>
|
template<class ...Args>
|
||||||
node_type(Args &&...args)
|
node_type(Args &&...args)
|
||||||
: value(boost::forward<Args>(args)...)
|
: value(boost::forward<Args>(args)...)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
#else //BOOST_CONTAINERS_PERFECT_FORWARDING
|
#else //BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
node_type()
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
: value()
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
{}
|
node_type(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
|
: value(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _)) \
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
{} \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
|
||||||
node_type(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
|
||||||
: value(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)) \
|
|
||||||
{} \
|
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif//BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif//BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
void set_pointer(VoidPointer p)
|
void set_pointer(VoidPointer p)
|
||||||
{ node_type_base<VoidPointer>::set_pointer(p); }
|
{ node_type_base<VoidPointer>::set_pointer(p); }
|
||||||
@@ -163,33 +158,38 @@ struct node_type
|
|||||||
template<typename T, typename Reference, typename Pointer>
|
template<typename T, typename Reference, typename Pointer>
|
||||||
class iterator
|
class iterator
|
||||||
: public std::iterator< std::random_access_iterator_tag
|
: public std::iterator< std::random_access_iterator_tag
|
||||||
, typename std::iterator_traits<Pointer>::value_type
|
, T
|
||||||
, typename std::iterator_traits<Pointer>::difference_type
|
, typename boost::intrusive::
|
||||||
|
pointer_traits<Pointer>::difference_type
|
||||||
, Pointer
|
, Pointer
|
||||||
, Reference>
|
, Reference>
|
||||||
{
|
{
|
||||||
|
typedef typename boost::intrusive::
|
||||||
|
pointer_traits<Pointer>::template
|
||||||
|
rebind_pointer<void>::type void_ptr;
|
||||||
|
typedef typename boost::intrusive::
|
||||||
|
pointer_traits<Pointer>::template
|
||||||
|
rebind_pointer<const void>::type const_void_ptr;
|
||||||
|
typedef node_type<void_ptr, T> node_type_t;
|
||||||
|
typedef typename boost::intrusive::
|
||||||
|
pointer_traits<Pointer>::template
|
||||||
|
rebind_pointer<node_type_t>::type node_type_ptr_t;
|
||||||
|
typedef typename boost::intrusive::
|
||||||
|
pointer_traits<Pointer>::template
|
||||||
|
rebind_pointer<const node_type_t>::type const_node_type_ptr_t;
|
||||||
|
typedef typename boost::intrusive::
|
||||||
|
pointer_traits<Pointer>::template
|
||||||
|
rebind_pointer<void_ptr>::type void_ptr_ptr;
|
||||||
|
|
||||||
typedef typename boost::pointer_to_other
|
friend class iterator<T, const T, typename boost::intrusive::pointer_traits<Pointer>::template rebind_pointer<T>::type>;
|
||||||
<Pointer, void>::type void_ptr;
|
|
||||||
typedef typename boost::pointer_to_other
|
|
||||||
<Pointer, const void>::type const_void_ptr;
|
|
||||||
typedef node_type<void_ptr, T> node_type_t;
|
|
||||||
typedef typename boost::pointer_to_other
|
|
||||||
<void_ptr, node_type_t>::type node_type_ptr_t;
|
|
||||||
typedef typename boost::pointer_to_other
|
|
||||||
<void_ptr, const node_type_t>::type const_node_type_ptr_t;
|
|
||||||
typedef typename boost::pointer_to_other
|
|
||||||
<void_ptr, void_ptr>::type void_ptr_ptr;
|
|
||||||
|
|
||||||
friend class iterator<T, const T, typename boost::pointer_to_other<Pointer, T>::type>;
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
typedef std::random_access_iterator_tag iterator_category;
|
typedef std::random_access_iterator_tag iterator_category;
|
||||||
typedef T value_type;
|
typedef T value_type;
|
||||||
typedef typename std::iterator_traits
|
typedef typename boost::intrusive::
|
||||||
<Pointer>::difference_type difference_type;
|
pointer_traits<Pointer>::difference_type difference_type;
|
||||||
typedef Pointer pointer;
|
typedef Pointer pointer;
|
||||||
typedef Reference reference;
|
typedef Reference reference;
|
||||||
|
|
||||||
iterator()
|
iterator()
|
||||||
{}
|
{}
|
||||||
@@ -198,27 +198,24 @@ class iterator
|
|||||||
: pn(pn)
|
: pn(pn)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
iterator(const iterator<T, T&, typename boost::pointer_to_other<Pointer, T>::type >& x)
|
iterator(const iterator<T, T&, typename boost::intrusive::pointer_traits<Pointer>::template rebind_pointer<T>::type>& x)
|
||||||
: pn(x.pn)
|
: pn(x.pn)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static node_type_ptr_t node_ptr_cast(const void_ptr &p)
|
static node_type_ptr_t node_ptr_cast(const void_ptr &p)
|
||||||
{
|
{
|
||||||
using boost::get_pointer;
|
return node_type_ptr_t(static_cast<node_type_t*>(stable_vector_detail::to_raw_pointer(p)));
|
||||||
return node_type_ptr_t(static_cast<node_type_t*>(stable_vector_detail::get_pointer(p)));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static const_node_type_ptr_t node_ptr_cast(const const_void_ptr &p)
|
static const_node_type_ptr_t node_ptr_cast(const const_void_ptr &p)
|
||||||
{
|
{
|
||||||
using boost::get_pointer;
|
return const_node_type_ptr_t(static_cast<const node_type_t*>(stable_vector_detail::to_raw_pointer(p)));
|
||||||
return const_node_type_ptr_t(static_cast<const node_type_t*>(stable_vector_detail::get_pointer(p)));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void_ptr_ptr void_ptr_ptr_cast(const void_ptr &p)
|
static void_ptr_ptr void_ptr_ptr_cast(const void_ptr &p)
|
||||||
{
|
{
|
||||||
using boost::get_pointer;
|
return void_ptr_ptr(static_cast<void_ptr*>(stable_vector_detail::to_raw_pointer(p)));
|
||||||
return void_ptr_ptr(static_cast<void_ptr*>(stable_vector_detail::get_pointer(p)));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
reference dereference() const
|
reference dereference() const
|
||||||
@@ -325,12 +322,15 @@ struct select_multiallocation_chain
|
|||||||
template<class A>
|
template<class A>
|
||||||
struct select_multiallocation_chain<A, 1>
|
struct select_multiallocation_chain<A, 1>
|
||||||
{
|
{
|
||||||
typedef typename A::template
|
typedef typename boost::intrusive::pointer_traits
|
||||||
rebind<void>::other::pointer void_ptr;
|
<typename allocator_traits<A>::pointer>::
|
||||||
typedef containers_detail::basic_multiallocation_chain
|
template rebind_pointer<void>::type void_ptr;
|
||||||
|
typedef container_detail::basic_multiallocation_chain
|
||||||
<void_ptr> multialloc_cached_counted;
|
<void_ptr> multialloc_cached_counted;
|
||||||
typedef boost::container::containers_detail::transform_multiallocation_chain
|
typedef boost::container::container_detail::
|
||||||
<multialloc_cached_counted, typename A::value_type> type;
|
transform_multiallocation_chain
|
||||||
|
< multialloc_cached_counted
|
||||||
|
, typename allocator_traits<A>::value_type> type;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace stable_vector_detail
|
} //namespace stable_vector_detail
|
||||||
@@ -389,59 +389,82 @@ template <class T, class A>
|
|||||||
class stable_vector
|
class stable_vector
|
||||||
{
|
{
|
||||||
///@cond
|
///@cond
|
||||||
typedef typename containers_detail::
|
typedef allocator_traits<A> allocator_traits_type;
|
||||||
move_const_ref_type<T>::type insert_const_ref_type;
|
typedef typename container_detail::
|
||||||
typedef typename A::template
|
move_const_ref_type<T>::type insert_const_ref_type;
|
||||||
rebind<void>::other::pointer void_ptr;
|
typedef typename boost::intrusive::pointer_traits
|
||||||
typedef typename boost::pointer_to_other
|
<typename allocator_traits_type::pointer>::
|
||||||
<void_ptr, const void>::type const_void_ptr;
|
template rebind_pointer<void>::type void_ptr;
|
||||||
typedef typename A::template
|
typedef typename boost::intrusive::pointer_traits
|
||||||
rebind<void_ptr>::other::pointer void_ptr_ptr;
|
<void_ptr>::template
|
||||||
typedef typename boost::pointer_to_other
|
rebind_pointer<const void>::type const_void_ptr;
|
||||||
<void_ptr, const void_ptr>::type const_void_ptr_ptr;
|
typedef typename boost::intrusive::pointer_traits
|
||||||
|
<void_ptr>::template
|
||||||
|
rebind_pointer<void_ptr>::type void_ptr_ptr;
|
||||||
|
typedef typename boost::intrusive::pointer_traits
|
||||||
|
<void_ptr>::template
|
||||||
|
rebind_pointer<const void_ptr>::type const_void_ptr_ptr;
|
||||||
typedef stable_vector_detail::node_type
|
typedef stable_vector_detail::node_type
|
||||||
<void_ptr, T> node_type_t;
|
<void_ptr, T> node_type_t;
|
||||||
typedef typename A::template
|
typedef typename boost::intrusive::pointer_traits
|
||||||
rebind<node_type_t>::other::pointer node_type_ptr_t;
|
<void_ptr>::template
|
||||||
|
rebind_pointer<node_type_t>::type node_type_ptr_t;
|
||||||
typedef stable_vector_detail::node_type_base
|
typedef stable_vector_detail::node_type_base
|
||||||
<void_ptr> node_type_base_t;
|
<void_ptr> node_type_base_t;
|
||||||
typedef typename A::template
|
typedef typename boost::intrusive::pointer_traits
|
||||||
rebind<node_type_base_t>::other::pointer node_type_base_ptr_t;
|
<void_ptr>::template
|
||||||
typedef
|
rebind_pointer<node_type_base_t>::type node_type_base_ptr_t;
|
||||||
::boost::container::vector<void_ptr,
|
typedef ::boost::container::vector<void_ptr,
|
||||||
typename A::
|
typename allocator_traits_type::
|
||||||
template rebind<void_ptr>::other
|
template portable_rebind_alloc
|
||||||
> impl_type;
|
<void_ptr>::type> impl_type;
|
||||||
typedef typename impl_type::iterator impl_iterator;
|
typedef typename impl_type::iterator impl_iterator;
|
||||||
typedef typename impl_type::const_iterator const_impl_iterator;
|
typedef typename impl_type::const_iterator const_impl_iterator;
|
||||||
|
|
||||||
typedef ::boost::container::containers_detail::
|
typedef ::boost::container::container_detail::
|
||||||
integral_constant<unsigned, 1> allocator_v1;
|
integral_constant<unsigned, 1> allocator_v1;
|
||||||
typedef ::boost::container::containers_detail::
|
typedef ::boost::container::container_detail::
|
||||||
integral_constant<unsigned, 2> allocator_v2;
|
integral_constant<unsigned, 2> allocator_v2;
|
||||||
typedef ::boost::container::containers_detail::integral_constant
|
typedef ::boost::container::container_detail::integral_constant
|
||||||
<unsigned, boost::container::containers_detail::
|
<unsigned, boost::container::container_detail::
|
||||||
version<A>::value> alloc_version;
|
version<A>::value> alloc_version;
|
||||||
typedef typename A::
|
typedef typename allocator_traits_type::
|
||||||
template rebind<node_type_t>::other node_allocator_type;
|
template portable_rebind_alloc
|
||||||
|
<node_type_t>::type node_allocator_type;
|
||||||
|
|
||||||
node_type_ptr_t allocate_one()
|
node_type_ptr_t allocate_one()
|
||||||
{ return this->allocate_one(alloc_version()); }
|
{ return this->allocate_one(alloc_version()); }
|
||||||
|
|
||||||
node_type_ptr_t allocate_one(allocator_v1)
|
template<class AllocatorVersion>
|
||||||
{ return get_al().allocate(1); }
|
node_type_ptr_t allocate_one(AllocatorVersion,
|
||||||
|
typename boost::container::container_detail::enable_if_c
|
||||||
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v1>
|
||||||
|
::value>::type * = 0)
|
||||||
|
{ return node_alloc().allocate(1); }
|
||||||
|
|
||||||
node_type_ptr_t allocate_one(allocator_v2)
|
template<class AllocatorVersion>
|
||||||
{ return get_al().allocate_one(); }
|
node_type_ptr_t allocate_one(AllocatorVersion,
|
||||||
|
typename boost::container::container_detail::enable_if_c
|
||||||
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v2>
|
||||||
|
::value>::type * = 0)
|
||||||
|
{ return node_alloc().allocate_one(); }
|
||||||
|
|
||||||
void deallocate_one(node_type_ptr_t p)
|
void deallocate_one(node_type_ptr_t p)
|
||||||
{ return this->deallocate_one(p, alloc_version()); }
|
{ return this->deallocate_one(p, alloc_version()); }
|
||||||
|
|
||||||
void deallocate_one(node_type_ptr_t p, allocator_v1)
|
template<class AllocatorVersion>
|
||||||
{ get_al().deallocate(p, 1); }
|
void deallocate_one(node_type_ptr_t p, AllocatorVersion,
|
||||||
|
typename boost::container::container_detail::enable_if_c
|
||||||
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v1>
|
||||||
|
::value>::type * = 0)
|
||||||
|
{ node_alloc().deallocate(p, 1); }
|
||||||
|
|
||||||
void deallocate_one(node_type_ptr_t p, allocator_v2)
|
template<class AllocatorVersion>
|
||||||
{ get_al().deallocate_one(p); }
|
void deallocate_one(node_type_ptr_t p, AllocatorVersion,
|
||||||
|
typename boost::container::container_detail::enable_if_c
|
||||||
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v2>
|
||||||
|
::value>::type * = 0)
|
||||||
|
{ node_alloc().deallocate_one(p); }
|
||||||
|
|
||||||
friend class stable_vector_detail::clear_on_destroy<stable_vector>;
|
friend class stable_vector_detail::clear_on_destroy<stable_vector>;
|
||||||
///@endcond
|
///@endcond
|
||||||
@@ -450,10 +473,10 @@ class stable_vector
|
|||||||
|
|
||||||
// types:
|
// types:
|
||||||
|
|
||||||
typedef typename A::reference reference;
|
typedef typename allocator_traits_type::reference reference;
|
||||||
typedef typename A::const_reference const_reference;
|
typedef typename allocator_traits_type::const_reference const_reference;
|
||||||
typedef typename A::pointer pointer;
|
typedef typename allocator_traits_type::pointer pointer;
|
||||||
typedef typename A::const_pointer const_pointer;
|
typedef typename allocator_traits_type::const_pointer const_pointer;
|
||||||
typedef stable_vector_detail::iterator
|
typedef stable_vector_detail::iterator
|
||||||
<T,T&, pointer> iterator;
|
<T,T&, pointer> iterator;
|
||||||
typedef stable_vector_detail::iterator
|
typedef stable_vector_detail::iterator
|
||||||
@@ -461,9 +484,10 @@ class stable_vector
|
|||||||
typedef typename impl_type::size_type size_type;
|
typedef typename impl_type::size_type size_type;
|
||||||
typedef typename iterator::difference_type difference_type;
|
typedef typename iterator::difference_type difference_type;
|
||||||
typedef T value_type;
|
typedef T value_type;
|
||||||
typedef A allocator_type;
|
typedef A allocator_type;
|
||||||
typedef std::reverse_iterator<iterator> reverse_iterator;
|
typedef std::reverse_iterator<iterator> reverse_iterator;
|
||||||
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
||||||
|
typedef node_allocator_type stored_allocator_type;
|
||||||
|
|
||||||
///@cond
|
///@cond
|
||||||
private:
|
private:
|
||||||
@@ -483,13 +507,24 @@ class stable_vector
|
|||||||
///@endcond
|
///@endcond
|
||||||
public:
|
public:
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Default constructs a stable_vector.
|
||||||
|
//!
|
||||||
|
//! <b>Throws</b>: If allocator_type's default constructor throws.
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
stable_vector()
|
||||||
|
: internal_data(), impl()
|
||||||
|
{
|
||||||
|
STABLE_VECTOR_CHECK_INVARIANT;
|
||||||
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs a stable_vector taking the allocator as parameter.
|
//! <b>Effects</b>: Constructs a stable_vector taking the allocator as parameter.
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
explicit stable_vector(const A& al=A())
|
explicit stable_vector(const A& al)
|
||||||
: internal_data(al),impl(al)
|
: internal_data(al),impl(al)
|
||||||
{
|
{
|
||||||
STABLE_VECTOR_CHECK_INVARIANT;
|
STABLE_VECTOR_CHECK_INVARIANT;
|
||||||
}
|
}
|
||||||
@@ -502,7 +537,7 @@ class stable_vector
|
|||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Linear to n.
|
//! <b>Complexity</b>: Linear to n.
|
||||||
explicit stable_vector(size_type n)
|
explicit stable_vector(size_type n)
|
||||||
: internal_data(A()),impl(A())
|
: internal_data(A()),impl(A())
|
||||||
{
|
{
|
||||||
stable_vector_detail::clear_on_destroy<stable_vector> cod(*this);
|
stable_vector_detail::clear_on_destroy<stable_vector> cod(*this);
|
||||||
this->resize(n);
|
this->resize(n);
|
||||||
@@ -518,7 +553,7 @@ class stable_vector
|
|||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Linear to n.
|
//! <b>Complexity</b>: Linear to n.
|
||||||
stable_vector(size_type n, const T& t, const A& al=A())
|
stable_vector(size_type n, const T& t, const A& al=A())
|
||||||
: internal_data(al),impl(al)
|
: internal_data(al),impl(al)
|
||||||
{
|
{
|
||||||
stable_vector_detail::clear_on_destroy<stable_vector> cod(*this);
|
stable_vector_detail::clear_on_destroy<stable_vector> cod(*this);
|
||||||
this->insert(this->cbegin(), n, t);
|
this->insert(this->cbegin(), n, t);
|
||||||
@@ -549,7 +584,10 @@ class stable_vector
|
|||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Linear to the elements x contains.
|
//! <b>Complexity</b>: Linear to the elements x contains.
|
||||||
stable_vector(const stable_vector& x)
|
stable_vector(const stable_vector& x)
|
||||||
: internal_data(x.get_al()),impl(x.get_al())
|
: internal_data(allocator_traits<node_allocator_type>::
|
||||||
|
select_on_container_copy_construction(x.node_alloc()))
|
||||||
|
, impl(allocator_traits<allocator_type>::
|
||||||
|
select_on_container_copy_construction(x.impl.get_stored_allocator()))
|
||||||
{
|
{
|
||||||
stable_vector_detail::clear_on_destroy<stable_vector> cod(*this);
|
stable_vector_detail::clear_on_destroy<stable_vector> cod(*this);
|
||||||
this->insert(this->cbegin(), x.begin(), x.end());
|
this->insert(this->cbegin(), x.begin(), x.end());
|
||||||
@@ -562,9 +600,11 @@ class stable_vector
|
|||||||
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
stable_vector(BOOST_RV_REF(stable_vector) x)
|
stable_vector(BOOST_RV_REF(stable_vector) x)
|
||||||
: internal_data(x.get_al()),impl(x.get_al())
|
: internal_data(boost::move(x.node_alloc())), impl(boost::move(x.impl))
|
||||||
{ this->swap(x); }
|
{
|
||||||
|
this->priv_swap_members(x);
|
||||||
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Destroys the stable_vector. All stored values are destroyed
|
//! <b>Effects</b>: Destroys the stable_vector. All stored values are destroyed
|
||||||
//! and used memory is deallocated.
|
//! and used memory is deallocated.
|
||||||
@@ -589,7 +629,17 @@ class stable_vector
|
|||||||
stable_vector& operator=(BOOST_COPY_ASSIGN_REF(stable_vector) x)
|
stable_vector& operator=(BOOST_COPY_ASSIGN_REF(stable_vector) x)
|
||||||
{
|
{
|
||||||
STABLE_VECTOR_CHECK_INVARIANT;
|
STABLE_VECTOR_CHECK_INVARIANT;
|
||||||
if (this != &x) {
|
if (&x != this){
|
||||||
|
node_allocator_type &this_alloc = this->node_alloc();
|
||||||
|
const node_allocator_type &x_alloc = x.node_alloc();
|
||||||
|
container_detail::bool_<allocator_traits_type::
|
||||||
|
propagate_on_container_copy_assignment::value> flag;
|
||||||
|
if(flag && this_alloc != x_alloc){
|
||||||
|
this->clear();
|
||||||
|
this->shrink_to_fit();
|
||||||
|
}
|
||||||
|
container_detail::assign_alloc(this->node_alloc(), x.node_alloc(), flag);
|
||||||
|
container_detail::assign_alloc(this->impl.get_stored_allocator(), x.impl.get_stored_allocator(), flag);
|
||||||
this->assign(x.begin(), x.end());
|
this->assign(x.begin(), x.end());
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
@@ -606,8 +656,25 @@ class stable_vector
|
|||||||
stable_vector& operator=(BOOST_RV_REF(stable_vector) x)
|
stable_vector& operator=(BOOST_RV_REF(stable_vector) x)
|
||||||
{
|
{
|
||||||
if (&x != this){
|
if (&x != this){
|
||||||
this->swap(x);
|
node_allocator_type &this_alloc = this->node_alloc();
|
||||||
x.clear();
|
node_allocator_type &x_alloc = x.node_alloc();
|
||||||
|
//If allocators are equal we can just swap pointers
|
||||||
|
if(this_alloc == x_alloc){
|
||||||
|
//Destroy objects but retain memory
|
||||||
|
this->clear();
|
||||||
|
this->impl = boost::move(x.impl);
|
||||||
|
this->priv_swap_members(x);
|
||||||
|
//Move allocator if needed
|
||||||
|
container_detail::bool_<allocator_traits_type::
|
||||||
|
propagate_on_container_move_assignment::value> flag;
|
||||||
|
container_detail::move_alloc(this->node_alloc(), x.node_alloc(), flag);
|
||||||
|
}
|
||||||
|
//If unequal allocators, then do a one by one move
|
||||||
|
else{
|
||||||
|
typedef typename std::iterator_traits<iterator>::iterator_category ItCat;
|
||||||
|
this->assign( boost::make_move_iterator(x.begin())
|
||||||
|
, boost::make_move_iterator(x.end()));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
@@ -641,7 +708,27 @@ class stable_vector
|
|||||||
//! <b>Throws</b>: If allocator's copy constructor throws.
|
//! <b>Throws</b>: If allocator's copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
allocator_type get_allocator()const {return get_al();}
|
allocator_type get_allocator()const {return node_alloc();}
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Returns a reference to the internal allocator.
|
||||||
|
//!
|
||||||
|
//! <b>Throws</b>: Nothing
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
//!
|
||||||
|
//! <b>Note</b>: Non-standard extension.
|
||||||
|
const stored_allocator_type &get_stored_allocator() const BOOST_CONTAINER_NOEXCEPT
|
||||||
|
{ return node_alloc(); }
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Returns a reference to the internal allocator.
|
||||||
|
//!
|
||||||
|
//! <b>Throws</b>: Nothing
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
//!
|
||||||
|
//! <b>Note</b>: Non-standard extension.
|
||||||
|
stored_allocator_type &get_stored_allocator() BOOST_CONTAINER_NOEXCEPT
|
||||||
|
{ return node_alloc(); }
|
||||||
|
|
||||||
|
|
||||||
//! <b>Effects</b>: Returns an iterator to the first element contained in the stable_vector.
|
//! <b>Effects</b>: Returns an iterator to the first element contained in the stable_vector.
|
||||||
@@ -946,7 +1033,8 @@ class stable_vector
|
|||||||
void push_back(T &x) { push_back(const_cast<const T &>(x)); }
|
void push_back(T &x) { push_back(const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
void push_back(const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
void push_back(const U &u, typename container_detail::enable_if_c
|
||||||
|
<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return priv_push_back(u); }
|
{ return priv_push_back(u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -982,7 +1070,8 @@ class stable_vector
|
|||||||
iterator insert(const_iterator position, T &x) { return this->insert(position, const_cast<const T &>(x)); }
|
iterator insert(const_iterator position, T &x) { return this->insert(position, const_cast<const T &>(x)); }
|
||||||
|
|
||||||
template<class U>
|
template<class U>
|
||||||
iterator insert(const_iterator position, const U &u, typename containers_detail::enable_if_c<containers_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
iterator insert(const_iterator position, const U &u, typename container_detail::enable_if_c
|
||||||
|
<container_detail::is_same<T, U>::value && !::boost::has_move_emulation_enabled<U>::value >::type* =0)
|
||||||
{ return this->priv_insert(position, u); }
|
{ return this->priv_insert(position, u); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -1035,7 +1124,7 @@ class stable_vector
|
|||||||
boost::mpl::not_<boost::is_integral<InputIterator> >());
|
boost::mpl::not_<boost::is_integral<InputIterator> >());
|
||||||
}
|
}
|
||||||
|
|
||||||
#if defined(BOOST_CONTAINERS_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
#if defined(BOOST_CONTAINER_PERFECT_FORWARDING) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
|
||||||
|
|
||||||
//! <b>Effects</b>: Inserts an object of type T constructed with
|
//! <b>Effects</b>: Inserts an object of type T constructed with
|
||||||
//! std::forward<Args>(args)... in the end of the stable_vector.
|
//! std::forward<Args>(args)... in the end of the stable_vector.
|
||||||
@@ -1046,7 +1135,7 @@ class stable_vector
|
|||||||
template<class ...Args>
|
template<class ...Args>
|
||||||
void emplace_back(Args &&...args)
|
void emplace_back(Args &&...args)
|
||||||
{
|
{
|
||||||
typedef emplace_functor<node_type_t, Args...> EmplaceFunctor;
|
typedef emplace_functor<Args...> EmplaceFunctor;
|
||||||
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator;
|
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator;
|
||||||
EmplaceFunctor &&ef = EmplaceFunctor(boost::forward<Args>(args)...);
|
EmplaceFunctor &&ef = EmplaceFunctor(boost::forward<Args>(args)...);
|
||||||
this->insert(this->cend(), EmplaceIterator(ef), EmplaceIterator());
|
this->insert(this->cend(), EmplaceIterator(ef), EmplaceIterator());
|
||||||
@@ -1066,7 +1155,7 @@ class stable_vector
|
|||||||
{
|
{
|
||||||
//Just call more general insert(pos, size, value) and return iterator
|
//Just call more general insert(pos, size, value) and return iterator
|
||||||
size_type pos_n = position - cbegin();
|
size_type pos_n = position - cbegin();
|
||||||
typedef emplace_functor<node_type_t, Args...> EmplaceFunctor;
|
typedef emplace_functor<Args...> EmplaceFunctor;
|
||||||
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator;
|
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator;
|
||||||
EmplaceFunctor &&ef = EmplaceFunctor(boost::forward<Args>(args)...);
|
EmplaceFunctor &&ef = EmplaceFunctor(boost::forward<Args>(args)...);
|
||||||
this->insert(position, EmplaceIterator(ef), EmplaceIterator());
|
this->insert(position, EmplaceIterator(ef), EmplaceIterator());
|
||||||
@@ -1075,51 +1164,40 @@ class stable_vector
|
|||||||
|
|
||||||
#else
|
#else
|
||||||
|
|
||||||
void emplace_back()
|
|
||||||
{
|
|
||||||
typedef emplace_functor<node_type_t> EmplaceFunctor;
|
|
||||||
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator;
|
|
||||||
EmplaceFunctor ef;
|
|
||||||
this->insert(this->cend(), EmplaceIterator(ef), EmplaceIterator());
|
|
||||||
}
|
|
||||||
|
|
||||||
iterator emplace(const_iterator position)
|
|
||||||
{
|
|
||||||
typedef emplace_functor<node_type_t> EmplaceFunctor;
|
|
||||||
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator;
|
|
||||||
EmplaceFunctor ef;
|
|
||||||
size_type pos_n = position - this->cbegin();
|
|
||||||
this->insert(position, EmplaceIterator(ef), EmplaceIterator());
|
|
||||||
return iterator(this->begin() + pos_n);
|
|
||||||
}
|
|
||||||
|
|
||||||
#define BOOST_PP_LOCAL_MACRO(n) \
|
#define BOOST_PP_LOCAL_MACRO(n) \
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
void emplace_back(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
void emplace_back(BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
typedef BOOST_PP_CAT(BOOST_PP_CAT(emplace_functor, n), arg) \
|
typedef BOOST_PP_CAT(BOOST_PP_CAT(emplace_functor, n), arg) \
|
||||||
<node_type_t, BOOST_PP_ENUM_PARAMS(n, P)> EmplaceFunctor; \
|
BOOST_PP_EXPR_IF(n, <) BOOST_PP_ENUM_PARAMS(n, P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
EmplaceFunctor; \
|
||||||
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator; \
|
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator; \
|
||||||
EmplaceFunctor ef(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
EmplaceFunctor ef BOOST_PP_LPAREN_IF(n) \
|
||||||
this->insert(this->cend(), EmplaceIterator(ef), EmplaceIterator()); \
|
BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) \
|
||||||
|
BOOST_PP_RPAREN_IF(n); \
|
||||||
|
this->insert(this->cend() , EmplaceIterator(ef), EmplaceIterator()); \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
|
BOOST_PP_EXPR_IF(n, template<) BOOST_PP_ENUM_PARAMS(n, class P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
iterator emplace(const_iterator pos, BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_LIST, _)) \
|
iterator emplace(const_iterator pos \
|
||||||
|
BOOST_PP_ENUM_TRAILING(n, BOOST_CONTAINER_PP_PARAM_LIST, _)) \
|
||||||
{ \
|
{ \
|
||||||
typedef BOOST_PP_CAT(BOOST_PP_CAT(emplace_functor, n), arg) \
|
typedef BOOST_PP_CAT(BOOST_PP_CAT(emplace_functor, n), arg) \
|
||||||
<node_type_t, BOOST_PP_ENUM_PARAMS(n, P)> EmplaceFunctor; \
|
BOOST_PP_EXPR_IF(n, <) BOOST_PP_ENUM_PARAMS(n, P) BOOST_PP_EXPR_IF(n, >) \
|
||||||
|
EmplaceFunctor; \
|
||||||
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator; \
|
typedef emplace_iterator<node_type_t, EmplaceFunctor, difference_type> EmplaceIterator; \
|
||||||
EmplaceFunctor ef(BOOST_PP_ENUM(n, BOOST_CONTAINERS_PP_PARAM_FORWARD, _)); \
|
EmplaceFunctor ef BOOST_PP_LPAREN_IF(n) \
|
||||||
|
BOOST_PP_ENUM(n, BOOST_CONTAINER_PP_PARAM_FORWARD, _) \
|
||||||
|
BOOST_PP_RPAREN_IF(n); \
|
||||||
size_type pos_n = pos - this->cbegin(); \
|
size_type pos_n = pos - this->cbegin(); \
|
||||||
this->insert(pos, EmplaceIterator(ef), EmplaceIterator()); \
|
this->insert(pos, EmplaceIterator(ef), EmplaceIterator()); \
|
||||||
return iterator(this->begin() + pos_n); \
|
return iterator(this->begin() + pos_n); \
|
||||||
} \
|
} \
|
||||||
//!
|
//!
|
||||||
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_CONTAINERS_MAX_CONSTRUCTOR_PARAMETERS)
|
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
|
||||||
#include BOOST_PP_LOCAL_ITERATE()
|
#include BOOST_PP_LOCAL_ITERATE()
|
||||||
|
|
||||||
#endif //#ifdef BOOST_CONTAINERS_PERFECT_FORWARDING
|
#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases the element at position pos.
|
//! <b>Effects</b>: Erases the element at position pos.
|
||||||
//!
|
//!
|
||||||
@@ -1148,8 +1226,6 @@ class stable_vector
|
|||||||
{ return priv_erase(first, last, alloc_version()); }
|
{ return priv_erase(first, last, alloc_version()); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Swaps the contents of *this and x.
|
//! <b>Effects</b>: Swaps the contents of *this and x.
|
||||||
//! If this->allocator_type() != x.allocator_type()
|
|
||||||
//! allocators are also swapped.
|
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
//!
|
//!
|
||||||
@@ -1157,7 +1233,11 @@ class stable_vector
|
|||||||
void swap(stable_vector & x)
|
void swap(stable_vector & x)
|
||||||
{
|
{
|
||||||
STABLE_VECTOR_CHECK_INVARIANT;
|
STABLE_VECTOR_CHECK_INVARIANT;
|
||||||
this->swap_impl(*this,x);
|
container_detail::bool_<allocator_traits_type::propagate_on_container_swap::value> flag;
|
||||||
|
container_detail::swap_alloc(this->node_alloc(), x.node_alloc(), flag);
|
||||||
|
//vector's allocator is swapped here
|
||||||
|
this->impl.swap(x.impl);
|
||||||
|
this->priv_swap_members(x);
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Erases all the elements of the stable_vector.
|
//! <b>Effects</b>: Erases all the elements of the stable_vector.
|
||||||
@@ -1181,7 +1261,8 @@ class stable_vector
|
|||||||
this->clear_pool();
|
this->clear_pool();
|
||||||
//If empty completely destroy the index, let's recover default-constructed state
|
//If empty completely destroy the index, let's recover default-constructed state
|
||||||
if(this->empty()){
|
if(this->empty()){
|
||||||
impl_type().swap(this->impl);
|
this->impl.clear();
|
||||||
|
this->impl.shrink_to_fit();
|
||||||
this->internal_data.set_end_pointer_to_default_constructed();
|
this->internal_data.set_end_pointer_to_default_constructed();
|
||||||
}
|
}
|
||||||
//Otherwise, try to shrink-to-fit the index and readjust pointers if necessary
|
//Otherwise, try to shrink-to-fit the index and readjust pointers if necessary
|
||||||
@@ -1209,7 +1290,11 @@ class stable_vector
|
|||||||
void priv_push_back(const value_type &t)
|
void priv_push_back(const value_type &t)
|
||||||
{ this->insert(end(), t); }
|
{ this->insert(end(), t); }
|
||||||
|
|
||||||
void clear_pool(allocator_v1)
|
template<class AllocatorVersion>
|
||||||
|
void clear_pool(AllocatorVersion,
|
||||||
|
typename boost::container::container_detail::enable_if_c
|
||||||
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v1>
|
||||||
|
::value>::type * = 0)
|
||||||
{
|
{
|
||||||
if(!impl.empty() && impl.back()){
|
if(!impl.empty() && impl.back()){
|
||||||
void_ptr &pool_first_ref = impl.end()[-2];
|
void_ptr &pool_first_ref = impl.end()[-2];
|
||||||
@@ -1227,15 +1312,18 @@ class stable_vector
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void clear_pool(allocator_v2)
|
template<class AllocatorVersion>
|
||||||
|
void clear_pool(AllocatorVersion,
|
||||||
|
typename boost::container::container_detail::enable_if_c
|
||||||
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v2>
|
||||||
|
::value>::type * = 0)
|
||||||
{
|
{
|
||||||
|
|
||||||
if(!impl.empty() && impl.back()){
|
if(!impl.empty() && impl.back()){
|
||||||
void_ptr &pool_first_ref = impl.end()[-2];
|
void_ptr &pool_first_ref = impl.end()[-2];
|
||||||
void_ptr &pool_last_ref = impl.back();
|
void_ptr &pool_last_ref = impl.back();
|
||||||
multiallocation_chain holder;
|
multiallocation_chain holder;
|
||||||
holder.incorporate_after(holder.before_begin(), pool_first_ref, pool_last_ref, internal_data.pool_size);
|
holder.incorporate_after(holder.before_begin(), pool_first_ref, pool_last_ref, internal_data.pool_size);
|
||||||
get_al().deallocate_individual(boost::move(holder));
|
node_alloc().deallocate_individual(boost::move(holder));
|
||||||
pool_first_ref = pool_last_ref = 0;
|
pool_first_ref = pool_last_ref = 0;
|
||||||
this->internal_data.pool_size = 0;
|
this->internal_data.pool_size = 0;
|
||||||
}
|
}
|
||||||
@@ -1251,7 +1339,11 @@ class stable_vector
|
|||||||
this->add_to_pool(n, alloc_version());
|
this->add_to_pool(n, alloc_version());
|
||||||
}
|
}
|
||||||
|
|
||||||
void add_to_pool(size_type n, allocator_v1)
|
template<class AllocatorVersion>
|
||||||
|
void add_to_pool(size_type n, AllocatorVersion,
|
||||||
|
typename boost::container::container_detail::enable_if_c
|
||||||
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v1>
|
||||||
|
::value>::type * = 0)
|
||||||
{
|
{
|
||||||
size_type remaining = n;
|
size_type remaining = n;
|
||||||
while(remaining--){
|
while(remaining--){
|
||||||
@@ -1259,14 +1351,18 @@ class stable_vector
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void add_to_pool(size_type n, allocator_v2)
|
template<class AllocatorVersion>
|
||||||
|
void add_to_pool(size_type n, AllocatorVersion,
|
||||||
|
typename boost::container::container_detail::enable_if_c
|
||||||
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v2>
|
||||||
|
::value>::type * = 0)
|
||||||
{
|
{
|
||||||
void_ptr &pool_first_ref = impl.end()[-2];
|
void_ptr &pool_first_ref = impl.end()[-2];
|
||||||
void_ptr &pool_last_ref = impl.back();
|
void_ptr &pool_last_ref = impl.back();
|
||||||
multiallocation_chain holder;
|
multiallocation_chain holder;
|
||||||
holder.incorporate_after(holder.before_begin(), pool_first_ref, pool_last_ref, internal_data.pool_size);
|
holder.incorporate_after(holder.before_begin(), pool_first_ref, pool_last_ref, internal_data.pool_size);
|
||||||
//BOOST_STATIC_ASSERT((::boost::has_move_emulation_enabled<multiallocation_chain>::value == true));
|
//BOOST_STATIC_ASSERT((::boost::has_move_emulation_enabled<multiallocation_chain>::value == true));
|
||||||
multiallocation_chain m (get_al().allocate_individual(n));
|
multiallocation_chain m (node_alloc().allocate_individual(n));
|
||||||
holder.splice_after(holder.before_begin(), m, m.before_begin(), m.last(), n);
|
holder.splice_after(holder.before_begin(), m, m.before_begin(), m.last(), n);
|
||||||
this->internal_data.pool_size += n;
|
this->internal_data.pool_size += n;
|
||||||
std::pair<void_ptr, void_ptr> data(holder.extract_data());
|
std::pair<void_ptr, void_ptr> data(holder.extract_data());
|
||||||
@@ -1375,8 +1471,8 @@ class stable_vector
|
|||||||
|
|
||||||
template<class AllocatorVersion>
|
template<class AllocatorVersion>
|
||||||
iterator priv_erase(const_iterator first, const_iterator last, AllocatorVersion,
|
iterator priv_erase(const_iterator first, const_iterator last, AllocatorVersion,
|
||||||
typename boost::container::containers_detail::enable_if_c
|
typename boost::container::container_detail::enable_if_c
|
||||||
<boost::container::containers_detail::is_same<AllocatorVersion, allocator_v2>
|
<boost::container::container_detail::is_same<AllocatorVersion, allocator_v2>
|
||||||
::value>::type * = 0)
|
::value>::type * = 0)
|
||||||
{
|
{
|
||||||
STABLE_VECTOR_CHECK_INVARIANT;
|
STABLE_VECTOR_CHECK_INVARIANT;
|
||||||
@@ -1385,14 +1481,12 @@ class stable_vector
|
|||||||
|
|
||||||
static node_type_ptr_t node_ptr_cast(const void_ptr &p)
|
static node_type_ptr_t node_ptr_cast(const void_ptr &p)
|
||||||
{
|
{
|
||||||
using boost::get_pointer;
|
return node_type_ptr_t(static_cast<node_type_t*>(stable_vector_detail::to_raw_pointer(p)));
|
||||||
return node_type_ptr_t(static_cast<node_type_t*>(stable_vector_detail::get_pointer(p)));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static node_type_base_ptr_t node_base_ptr_cast(const void_ptr &p)
|
static node_type_base_ptr_t node_base_ptr_cast(const void_ptr &p)
|
||||||
{
|
{
|
||||||
using boost::get_pointer;
|
return node_type_base_ptr_t(static_cast<node_type_base_t*>(stable_vector_detail::to_raw_pointer(p)));
|
||||||
return node_type_base_ptr_t(static_cast<node_type_base_t*>(stable_vector_detail::get_pointer(p)));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static value_type& value(const void_ptr &p)
|
static value_type& value(const void_ptr &p)
|
||||||
@@ -1434,7 +1528,7 @@ class stable_vector
|
|||||||
{
|
{
|
||||||
node_type_ptr_t p = this->allocate_one();
|
node_type_ptr_t p = this->allocate_one();
|
||||||
try{
|
try{
|
||||||
boost::container::construct_in_place(&*p, it);
|
boost::container::construct_in_place(this->node_alloc(), &*p, it);
|
||||||
p->set_pointer(up);
|
p->set_pointer(up);
|
||||||
}
|
}
|
||||||
catch(...){
|
catch(...){
|
||||||
@@ -1516,7 +1610,7 @@ class stable_vector
|
|||||||
template <class FwdIterator>
|
template <class FwdIterator>
|
||||||
void insert_iter_fwd_alloc(const impl_iterator it, FwdIterator first, FwdIterator last, difference_type n, allocator_v2)
|
void insert_iter_fwd_alloc(const impl_iterator it, FwdIterator first, FwdIterator last, difference_type n, allocator_v2)
|
||||||
{
|
{
|
||||||
multiallocation_chain mem(get_al().allocate_individual(n));
|
multiallocation_chain mem(node_alloc().allocate_individual(n));
|
||||||
|
|
||||||
size_type i = 0;
|
size_type i = 0;
|
||||||
node_type_ptr_t p = 0;
|
node_type_ptr_t p = 0;
|
||||||
@@ -1525,7 +1619,7 @@ class stable_vector
|
|||||||
p = mem.front();
|
p = mem.front();
|
||||||
mem.pop_front();
|
mem.pop_front();
|
||||||
//This can throw
|
//This can throw
|
||||||
boost::container::construct_in_place(&*p, first);
|
boost::container::construct_in_place(this->node_alloc(), &*p, first);
|
||||||
p->set_pointer(void_ptr_ptr(&it[i]));
|
p->set_pointer(void_ptr_ptr(&it[i]));
|
||||||
++first;
|
++first;
|
||||||
it[i] = p;
|
it[i] = p;
|
||||||
@@ -1533,8 +1627,8 @@ class stable_vector
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch(...){
|
catch(...){
|
||||||
get_al().deallocate_one(p);
|
node_alloc().deallocate_one(p);
|
||||||
get_al().deallocate_many(boost::move(mem));
|
node_alloc().deallocate_many(boost::move(mem));
|
||||||
impl_iterator e = impl.erase(it+i, it+n);
|
impl_iterator e = impl.erase(it+i, it+n);
|
||||||
this->align_nodes(e, get_last_align());
|
this->align_nodes(e, get_last_align());
|
||||||
throw;
|
throw;
|
||||||
@@ -1548,13 +1642,13 @@ class stable_vector
|
|||||||
node_type_ptr_t p = 0;
|
node_type_ptr_t p = 0;
|
||||||
try{
|
try{
|
||||||
while(first != last){
|
while(first != last){
|
||||||
p = get_from_pool();
|
p = this->get_from_pool();
|
||||||
if(!p){
|
if(!p){
|
||||||
insert_iter_fwd_alloc(it+i, first, last, n-i, alloc_version());
|
insert_iter_fwd_alloc(it+i, first, last, n-i, alloc_version());
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
//This can throw
|
//This can throw
|
||||||
boost::container::construct_in_place(&*p, first);
|
boost::container::construct_in_place(this->node_alloc(), &*p, first);
|
||||||
p->set_pointer(void_ptr_ptr(&it[i]));
|
p->set_pointer(void_ptr_ptr(&it[i]));
|
||||||
++first;
|
++first;
|
||||||
it[i]=p;
|
it[i]=p;
|
||||||
@@ -1575,16 +1669,6 @@ class stable_vector
|
|||||||
this->insert_not_iter(position, first, last);
|
this->insert_not_iter(position, first, last);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void swap_impl(stable_vector& x,stable_vector& y)
|
|
||||||
{
|
|
||||||
using std::swap;
|
|
||||||
swap(x.get_al(),y.get_al());
|
|
||||||
swap(x.impl,y.impl);
|
|
||||||
swap(x.internal_data.pool_size, y.internal_data.pool_size);
|
|
||||||
x.readjust_end_node();
|
|
||||||
y.readjust_end_node();
|
|
||||||
}
|
|
||||||
|
|
||||||
#if defined(STABLE_VECTOR_ENABLE_INVARIANT_CHECKING)
|
#if defined(STABLE_VECTOR_ENABLE_INVARIANT_CHECKING)
|
||||||
bool invariant()const
|
bool invariant()const
|
||||||
{
|
{
|
||||||
@@ -1609,9 +1693,12 @@ class stable_vector
|
|||||||
return n >= num_pool;
|
return n >= num_pool;
|
||||||
}
|
}
|
||||||
|
|
||||||
class invariant_checker:private boost::noncopyable
|
class invariant_checker
|
||||||
{
|
{
|
||||||
|
invariant_checker(const invariant_checker &);
|
||||||
|
invariant_checker & operator=(const invariant_checker &);
|
||||||
const stable_vector* p;
|
const stable_vector* p;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
invariant_checker(const stable_vector& v):p(&v){}
|
invariant_checker(const stable_vector& v):p(&v){}
|
||||||
~invariant_checker(){BOOST_ASSERT(p->invariant());}
|
~invariant_checker(){BOOST_ASSERT(p->invariant());}
|
||||||
@@ -1619,11 +1706,32 @@ class stable_vector
|
|||||||
};
|
};
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
struct ebo_holder
|
class ebo_holder
|
||||||
: node_allocator_type
|
: public node_allocator_type
|
||||||
{
|
{
|
||||||
ebo_holder(const allocator_type &a)
|
private:
|
||||||
: node_allocator_type(a), pool_size(0), end_node()
|
BOOST_MOVABLE_BUT_NOT_COPYABLE(ebo_holder)
|
||||||
|
public:
|
||||||
|
/*
|
||||||
|
explicit ebo_holder(BOOST_RV_REF(ebo_holder) x)
|
||||||
|
: node_allocator_type(boost::move(static_cast<node_allocator_type&>(x)))
|
||||||
|
, pool_size(0)
|
||||||
|
, end_node()
|
||||||
|
{}
|
||||||
|
*/
|
||||||
|
template<class AllocatorRLValue>
|
||||||
|
explicit ebo_holder(BOOST_FWD_REF(AllocatorRLValue) a)
|
||||||
|
: node_allocator_type(boost::forward<AllocatorRLValue>(a))
|
||||||
|
, pool_size(0)
|
||||||
|
, end_node()
|
||||||
|
{
|
||||||
|
this->set_end_pointer_to_default_constructed();
|
||||||
|
}
|
||||||
|
|
||||||
|
ebo_holder()
|
||||||
|
: node_allocator_type()
|
||||||
|
, pool_size(0)
|
||||||
|
, end_node()
|
||||||
{
|
{
|
||||||
this->set_end_pointer_to_default_constructed();
|
this->set_end_pointer_to_default_constructed();
|
||||||
}
|
}
|
||||||
@@ -1637,8 +1745,15 @@ class stable_vector
|
|||||||
node_type_base_t end_node;
|
node_type_base_t end_node;
|
||||||
} internal_data;
|
} internal_data;
|
||||||
|
|
||||||
node_allocator_type &get_al() { return internal_data; }
|
void priv_swap_members(stable_vector &x)
|
||||||
const node_allocator_type &get_al() const { return internal_data; }
|
{
|
||||||
|
container_detail::do_swap(this->internal_data.pool_size, x.internal_data.pool_size);
|
||||||
|
this->readjust_end_node();
|
||||||
|
x.readjust_end_node();
|
||||||
|
}
|
||||||
|
|
||||||
|
node_allocator_type &node_alloc() { return internal_data; }
|
||||||
|
const node_allocator_type &node_alloc() const { return internal_data; }
|
||||||
|
|
||||||
impl_type impl;
|
impl_type impl;
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
@@ -30,8 +30,8 @@
|
|||||||
// representations about the suitability of this software for any
|
// representations about the suitability of this software for any
|
||||||
// purpose. It is provided "as is" without express or implied warranty.
|
// purpose. It is provided "as is" without express or implied warranty.
|
||||||
|
|
||||||
#ifndef BOOST_CONTAINERS_STRING_HPP
|
#ifndef BOOST_CONTAINER_STRING_HPP
|
||||||
#define BOOST_CONTAINERS_STRING_HPP
|
#define BOOST_CONTAINER_STRING_HPP
|
||||||
|
|
||||||
#include <boost/container/detail/config_begin.hpp>
|
#include <boost/container/detail/config_begin.hpp>
|
||||||
#include <boost/container/detail/workaround.hpp>
|
#include <boost/container/detail/workaround.hpp>
|
||||||
@@ -43,6 +43,7 @@
|
|||||||
#include <boost/container/detail/algorithms.hpp>
|
#include <boost/container/detail/algorithms.hpp>
|
||||||
#include <boost/container/detail/version_type.hpp>
|
#include <boost/container/detail/version_type.hpp>
|
||||||
#include <boost/container/detail/allocation_type.hpp>
|
#include <boost/container/detail/allocation_type.hpp>
|
||||||
|
#include <boost/container/allocator/allocator_traits.hpp>
|
||||||
#include <boost/container/detail/mpl.hpp>
|
#include <boost/container/detail/mpl.hpp>
|
||||||
#include <boost/move/move.hpp>
|
#include <boost/move/move.hpp>
|
||||||
#include <boost/static_assert.hpp>
|
#include <boost/static_assert.hpp>
|
||||||
@@ -75,7 +76,7 @@ namespace container {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
/// @cond
|
/// @cond
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
// ------------------------------------------------------------
|
// ------------------------------------------------------------
|
||||||
// Class basic_string_base.
|
// Class basic_string_base.
|
||||||
|
|
||||||
@@ -89,16 +90,20 @@ namespace containers_detail {
|
|||||||
template <class A>
|
template <class A>
|
||||||
class basic_string_base
|
class basic_string_base
|
||||||
{
|
{
|
||||||
basic_string_base();
|
|
||||||
BOOST_MOVABLE_BUT_NOT_COPYABLE(basic_string_base)
|
BOOST_MOVABLE_BUT_NOT_COPYABLE(basic_string_base)
|
||||||
|
|
||||||
|
typedef allocator_traits<A> allocator_traits_type;
|
||||||
public:
|
public:
|
||||||
typedef A allocator_type;
|
typedef A allocator_type;
|
||||||
//! The stored allocator type
|
//! The stored allocator type
|
||||||
typedef allocator_type stored_allocator_type;
|
typedef allocator_type stored_allocator_type;
|
||||||
typedef typename A::pointer pointer;
|
typedef typename allocator_traits_type::pointer pointer;
|
||||||
typedef typename A::value_type value_type;
|
typedef typename allocator_traits_type::value_type value_type;
|
||||||
typedef typename A::size_type size_type;
|
typedef typename allocator_traits_type::size_type size_type;
|
||||||
|
|
||||||
|
basic_string_base()
|
||||||
|
: members_()
|
||||||
|
{ init(); }
|
||||||
|
|
||||||
basic_string_base(const allocator_type& a)
|
basic_string_base(const allocator_type& a)
|
||||||
: members_(a)
|
: members_(a)
|
||||||
@@ -112,16 +117,16 @@ class basic_string_base
|
|||||||
}
|
}
|
||||||
|
|
||||||
basic_string_base(BOOST_RV_REF(basic_string_base) b)
|
basic_string_base(BOOST_RV_REF(basic_string_base) b)
|
||||||
: members_(b.members_)
|
: members_(boost::move(b.alloc()))
|
||||||
{
|
{
|
||||||
init();
|
this->init();
|
||||||
this->swap(b);
|
this->swap_data(b);
|
||||||
}
|
}
|
||||||
|
|
||||||
~basic_string_base()
|
~basic_string_base()
|
||||||
{
|
{
|
||||||
this->deallocate_block();
|
|
||||||
if(!this->is_short()){
|
if(!this->is_short()){
|
||||||
|
this->deallocate_block();
|
||||||
static_cast<long_t*>(static_cast<void*>(&this->members_.m_repr.r))->~long_t();
|
static_cast<long_t*>(static_cast<void*>(&this->members_.m_repr.r))->~long_t();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -169,14 +174,14 @@ class basic_string_base
|
|||||||
//so, unlike long_t, it can be placed in a union
|
//so, unlike long_t, it can be placed in a union
|
||||||
|
|
||||||
typedef typename boost::aligned_storage< sizeof(long_t),
|
typedef typename boost::aligned_storage< sizeof(long_t),
|
||||||
containers_detail::alignment_of<long_t>::value>::type long_raw_t;
|
container_detail::alignment_of<long_t>::value>::type long_raw_t;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
static const size_type MinInternalBufferChars = 8;
|
static const size_type MinInternalBufferChars = 8;
|
||||||
static const size_type AlignmentOfValueType =
|
static const size_type AlignmentOfValueType =
|
||||||
alignment_of<value_type>::value;
|
alignment_of<value_type>::value;
|
||||||
static const size_type ShortDataOffset =
|
static const size_type ShortDataOffset =
|
||||||
containers_detail::ct_rounded_size<sizeof(short_header), AlignmentOfValueType>::value;
|
container_detail::ct_rounded_size<sizeof(short_header), AlignmentOfValueType>::value;
|
||||||
static const size_type ZeroCostInternalBufferChars =
|
static const size_type ZeroCostInternalBufferChars =
|
||||||
(sizeof(long_t) - ShortDataOffset)/sizeof(value_type);
|
(sizeof(long_t) - ShortDataOffset)/sizeof(value_type);
|
||||||
static const size_type UnalignedFinalInternalBufferChars =
|
static const size_type UnalignedFinalInternalBufferChars =
|
||||||
@@ -204,8 +209,13 @@ class basic_string_base
|
|||||||
struct members_holder
|
struct members_holder
|
||||||
: public A
|
: public A
|
||||||
{
|
{
|
||||||
members_holder(const A &a)
|
members_holder()
|
||||||
: A(a)
|
: A()
|
||||||
|
{}
|
||||||
|
|
||||||
|
template<class AllocatorConvertible>
|
||||||
|
explicit members_holder(BOOST_FWD_REF(AllocatorConvertible) a)
|
||||||
|
: A(boost::forward<AllocatorConvertible>(a))
|
||||||
{}
|
{}
|
||||||
|
|
||||||
repr_t m_repr;
|
repr_t m_repr;
|
||||||
@@ -247,10 +257,10 @@ class basic_string_base
|
|||||||
|
|
||||||
protected:
|
protected:
|
||||||
|
|
||||||
typedef containers_detail::integral_constant<unsigned, 1> allocator_v1;
|
typedef container_detail::integral_constant<unsigned, 1> allocator_v1;
|
||||||
typedef containers_detail::integral_constant<unsigned, 2> allocator_v2;
|
typedef container_detail::integral_constant<unsigned, 2> allocator_v2;
|
||||||
typedef containers_detail::integral_constant<unsigned,
|
typedef container_detail::integral_constant<unsigned,
|
||||||
boost::container::containers_detail::version<A>::value> alloc_version;
|
boost::container::container_detail::version<A>::value> alloc_version;
|
||||||
|
|
||||||
std::pair<pointer, bool>
|
std::pair<pointer, bool>
|
||||||
allocation_command(allocation_type command,
|
allocation_command(allocation_type command,
|
||||||
@@ -295,7 +305,7 @@ class basic_string_base
|
|||||||
}
|
}
|
||||||
|
|
||||||
size_type next_capacity(size_type additional_objects) const
|
size_type next_capacity(size_type additional_objects) const
|
||||||
{ return get_next_capacity(this->alloc().max_size(), this->priv_storage(), additional_objects); }
|
{ return get_next_capacity(allocator_traits_type::max_size(this->alloc()), this->priv_storage(), additional_objects); }
|
||||||
|
|
||||||
void deallocate(pointer p, size_type n)
|
void deallocate(pointer p, size_type n)
|
||||||
{
|
{
|
||||||
@@ -304,16 +314,16 @@ class basic_string_base
|
|||||||
}
|
}
|
||||||
|
|
||||||
void construct(pointer p, const value_type &value = value_type())
|
void construct(pointer p, const value_type &value = value_type())
|
||||||
{ new((void*)containers_detail::get_pointer(p)) value_type(value); }
|
{ new((void*)container_detail::to_raw_pointer(p)) value_type(value); }
|
||||||
|
|
||||||
void destroy(pointer p, size_type n)
|
void destroy(pointer p, size_type n)
|
||||||
{
|
{
|
||||||
for(; n--; ++p)
|
for(; n--; ++p)
|
||||||
containers_detail::get_pointer(p)->~value_type();
|
container_detail::to_raw_pointer(p)->~value_type();
|
||||||
}
|
}
|
||||||
|
|
||||||
void destroy(pointer p)
|
void destroy(pointer p)
|
||||||
{ containers_detail::get_pointer(p)->~value_type(); }
|
{ container_detail::to_raw_pointer(p)->~value_type(); }
|
||||||
|
|
||||||
void allocate_initial_block(size_type n)
|
void allocate_initial_block(size_type n)
|
||||||
{
|
{
|
||||||
@@ -335,7 +345,7 @@ class basic_string_base
|
|||||||
{ this->deallocate(this->priv_addr(), this->priv_storage()); }
|
{ this->deallocate(this->priv_addr(), this->priv_storage()); }
|
||||||
|
|
||||||
size_type max_size() const
|
size_type max_size() const
|
||||||
{ return this->alloc().max_size() - 1; }
|
{ return allocator_traits_type::max_size(this->alloc()) - 1; }
|
||||||
|
|
||||||
// Helper functions for exception handling.
|
// Helper functions for exception handling.
|
||||||
void throw_length_error() const
|
void throw_length_error() const
|
||||||
@@ -404,14 +414,14 @@ class basic_string_base
|
|||||||
|
|
||||||
void priv_long_size(size_type sz)
|
void priv_long_size(size_type sz)
|
||||||
{
|
{
|
||||||
this->members_.m_repr.long_repr().length = static_cast<typename A::size_type>(sz);
|
this->members_.m_repr.long_repr().length = static_cast<typename allocator_traits_type::size_type>(sz);
|
||||||
}
|
}
|
||||||
|
|
||||||
void swap(basic_string_base& other)
|
void swap_data(basic_string_base& other)
|
||||||
{
|
{
|
||||||
if(this->is_short()){
|
if(this->is_short()){
|
||||||
if(other.is_short()){
|
if(other.is_short()){
|
||||||
std::swap(this->members_.m_repr, other.members_.m_repr);
|
container_detail::do_swap(this->members_.m_repr, other.members_.m_repr);
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
repr_t copied(this->members_.m_repr);
|
repr_t copied(this->members_.m_repr);
|
||||||
@@ -426,18 +436,13 @@ class basic_string_base
|
|||||||
this->members_.m_repr = copied;
|
this->members_.m_repr = copied;
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
std::swap(this->members_.m_repr.long_repr(), other.members_.m_repr.long_repr());
|
container_detail::do_swap(this->members_.m_repr.long_repr(), other.members_.m_repr.long_repr());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
allocator_type & this_al = this->alloc(), &other_al = other.alloc();
|
|
||||||
if(this_al != other_al){
|
|
||||||
containers_detail::do_swap(this_al, other_al);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
|
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
@@ -475,12 +480,13 @@ template <class CharT, class Traits = std::char_traits<CharT>, class A = std::al
|
|||||||
template <class CharT, class Traits, class A>
|
template <class CharT, class Traits, class A>
|
||||||
#endif
|
#endif
|
||||||
class basic_string
|
class basic_string
|
||||||
: private containers_detail::basic_string_base<A>
|
: private container_detail::basic_string_base<A>
|
||||||
{
|
{
|
||||||
/// @cond
|
/// @cond
|
||||||
private:
|
private:
|
||||||
|
typedef allocator_traits<A> allocator_traits_type;
|
||||||
BOOST_COPYABLE_AND_MOVABLE(basic_string)
|
BOOST_COPYABLE_AND_MOVABLE(basic_string)
|
||||||
typedef containers_detail::basic_string_base<A> base_t;
|
typedef container_detail::basic_string_base<A> base_t;
|
||||||
static const typename base_t::size_type InternalBufferChars = base_t::InternalBufferChars;
|
static const typename base_t::size_type InternalBufferChars = base_t::InternalBufferChars;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
@@ -527,17 +533,17 @@ class basic_string
|
|||||||
//! The second template parameter Traits
|
//! The second template parameter Traits
|
||||||
typedef Traits traits_type;
|
typedef Traits traits_type;
|
||||||
//! Pointer to CharT
|
//! Pointer to CharT
|
||||||
typedef typename A::pointer pointer;
|
typedef typename allocator_traits_type::pointer pointer;
|
||||||
//! Const pointer to CharT
|
//! Const pointer to CharT
|
||||||
typedef typename A::const_pointer const_pointer;
|
typedef typename allocator_traits_type::const_pointer const_pointer;
|
||||||
//! Reference to CharT
|
//! Reference to CharT
|
||||||
typedef typename A::reference reference;
|
typedef typename allocator_traits_type::reference reference;
|
||||||
//! Const reference to CharT
|
//! Const reference to CharT
|
||||||
typedef typename A::const_reference const_reference;
|
typedef typename allocator_traits_type::const_reference const_reference;
|
||||||
//! An unsigned integral type
|
//! An unsigned integral type
|
||||||
typedef typename A::size_type size_type;
|
typedef typename allocator_traits_type::size_type size_type;
|
||||||
//! A signed integral type
|
//! A signed integral type
|
||||||
typedef typename A::difference_type difference_type;
|
typedef typename allocator_traits_type::difference_type difference_type;
|
||||||
//! Iterator used to iterate through a string. It's a Random Access Iterator
|
//! Iterator used to iterate through a string. It's a Random Access Iterator
|
||||||
typedef pointer iterator;
|
typedef pointer iterator;
|
||||||
//! Const iterator used to iterate through a string. It's a Random Access Iterator
|
//! Const iterator used to iterate through a string. It's a Random Access Iterator
|
||||||
@@ -562,17 +568,28 @@ class basic_string
|
|||||||
struct reserve_t {};
|
struct reserve_t {};
|
||||||
|
|
||||||
basic_string(reserve_t, size_type n,
|
basic_string(reserve_t, size_type n,
|
||||||
const allocator_type& a = allocator_type())
|
const allocator_type& a = allocator_type())
|
||||||
: base_t(a, n + 1)
|
//Select allocator as in copy constructor as reserve_t-based constructors
|
||||||
|
//are two step copies optimized for capacity
|
||||||
|
: base_t( allocator_traits_type::select_on_container_copy_construction(a)
|
||||||
|
, n + 1)
|
||||||
{ this->priv_terminate_string(); }
|
{ this->priv_terminate_string(); }
|
||||||
|
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Default constructs a basic_string.
|
||||||
|
//!
|
||||||
|
//! <b>Throws</b>: If allocator_type's default constructor throws.
|
||||||
|
basic_string()
|
||||||
|
: base_t()
|
||||||
|
{ this->priv_terminate_string(); }
|
||||||
|
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs a basic_string taking the allocator as parameter.
|
//! <b>Effects</b>: Constructs a basic_string taking the allocator as parameter.
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
||||||
explicit basic_string(const allocator_type& a = allocator_type())
|
explicit basic_string(const allocator_type& a)
|
||||||
: base_t(a, InternalBufferChars)
|
: base_t(a)
|
||||||
{ this->priv_terminate_string(); }
|
{ this->priv_terminate_string(); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Copy constructs a basic_string.
|
//! <b>Effects</b>: Copy constructs a basic_string.
|
||||||
@@ -581,7 +598,7 @@ class basic_string
|
|||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: If allocator_type's default constructor or copy constructor throws.
|
//! <b>Throws</b>: If allocator_type's default constructor or copy constructor throws.
|
||||||
basic_string(const basic_string& s)
|
basic_string(const basic_string& s)
|
||||||
: base_t(s.alloc())
|
: base_t(allocator_traits_type::select_on_container_copy_construction(s.alloc()))
|
||||||
{ this->priv_range_initialize(s.begin(), s.end()); }
|
{ this->priv_range_initialize(s.begin(), s.end()); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Move constructor. Moves mx's resources to *this.
|
//! <b>Effects</b>: Move constructor. Moves mx's resources to *this.
|
||||||
@@ -603,7 +620,7 @@ class basic_string
|
|||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
else
|
else
|
||||||
this->priv_range_initialize
|
this->priv_range_initialize
|
||||||
(s.begin() + pos, s.begin() + pos + containers_detail::min_value(n, s.size() - pos));
|
(s.begin() + pos, s.begin() + pos + container_detail::min_value(n, s.size() - pos));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Constructs a basic_string taking the allocator as parameter,
|
//! <b>Effects</b>: Constructs a basic_string taking the allocator as parameter,
|
||||||
@@ -638,8 +655,8 @@ class basic_string
|
|||||||
: base_t(a)
|
: base_t(a)
|
||||||
{
|
{
|
||||||
//Dispatch depending on integer/iterator
|
//Dispatch depending on integer/iterator
|
||||||
const bool aux_boolean = containers_detail::is_convertible<InputIterator, size_type>::value;
|
const bool aux_boolean = container_detail::is_convertible<InputIterator, size_type>::value;
|
||||||
typedef containers_detail::bool_<aux_boolean> Result;
|
typedef container_detail::bool_<aux_boolean> Result;
|
||||||
this->priv_initialize_dispatch(f, l, Result());
|
this->priv_initialize_dispatch(f, l, Result());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -656,10 +673,24 @@ class basic_string
|
|||||||
//! <b>Postcondition</b>: x == *this.
|
//! <b>Postcondition</b>: x == *this.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Linear to the elements x contains.
|
//! <b>Complexity</b>: Linear to the elements x contains.
|
||||||
basic_string& operator=(BOOST_COPY_ASSIGN_REF(basic_string) s)
|
basic_string& operator=(BOOST_COPY_ASSIGN_REF(basic_string) x)
|
||||||
{
|
{
|
||||||
if (&s != this)
|
if (&x != this){
|
||||||
this->assign(s.begin(), s.end());
|
allocator_type &this_alloc = this->alloc();
|
||||||
|
const allocator_type &x_alloc = x.alloc();
|
||||||
|
container_detail::bool_<allocator_traits_type::
|
||||||
|
propagate_on_container_copy_assignment::value> flag;
|
||||||
|
if(flag && this_alloc != x_alloc){
|
||||||
|
if(!this->is_short()){
|
||||||
|
this->deallocate_block();
|
||||||
|
this->is_short(true);
|
||||||
|
Traits::assign(*this->priv_addr(), this->priv_null());
|
||||||
|
this->priv_size(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
container_detail::assign_alloc(this->alloc(), x.alloc(), flag);
|
||||||
|
this->assign(x.begin(), x.end());
|
||||||
|
}
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -668,11 +699,25 @@ class basic_string
|
|||||||
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
//! <b>Throws</b>: If allocator_type's copy constructor throws.
|
||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: Constant.
|
//! <b>Complexity</b>: Constant.
|
||||||
basic_string& operator=(BOOST_RV_REF(basic_string) ms)
|
basic_string& operator=(BOOST_RV_REF(basic_string) x)
|
||||||
{
|
{
|
||||||
basic_string &s = ms;
|
if (&x != this){
|
||||||
if (&s != this){
|
allocator_type &this_alloc = this->alloc();
|
||||||
this->swap(s);
|
allocator_type &x_alloc = x.alloc();
|
||||||
|
//If allocators are equal we can just swap pointers
|
||||||
|
if(this_alloc == x_alloc){
|
||||||
|
//Destroy objects but retain memory in case x reuses it in the future
|
||||||
|
this->clear();
|
||||||
|
this->swap_data(x);
|
||||||
|
//Move allocator if needed
|
||||||
|
container_detail::bool_<allocator_traits_type::
|
||||||
|
propagate_on_container_move_assignment::value> flag;
|
||||||
|
container_detail::move_alloc(this_alloc, x_alloc, flag);
|
||||||
|
}
|
||||||
|
//If unequal allocators, then do a one by one move
|
||||||
|
else{
|
||||||
|
this->assign( x.begin(), x.end());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
@@ -709,7 +754,6 @@ class basic_string
|
|||||||
const_iterator cbegin() const
|
const_iterator cbegin() const
|
||||||
{ return this->priv_addr(); }
|
{ return this->priv_addr(); }
|
||||||
|
|
||||||
|
|
||||||
//! <b>Effects</b>: Returns an iterator to the end of the vector.
|
//! <b>Effects</b>: Returns an iterator to the end of the vector.
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
@@ -796,6 +840,26 @@ class basic_string
|
|||||||
allocator_type get_allocator() const
|
allocator_type get_allocator() const
|
||||||
{ return this->alloc(); }
|
{ return this->alloc(); }
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Returns a reference to the internal allocator.
|
||||||
|
//!
|
||||||
|
//! <b>Throws</b>: Nothing
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
//!
|
||||||
|
//! <b>Note</b>: Non-standard extension.
|
||||||
|
const stored_allocator_type &get_stored_allocator() const BOOST_CONTAINER_NOEXCEPT
|
||||||
|
{ return this->alloc(); }
|
||||||
|
|
||||||
|
//! <b>Effects</b>: Returns a reference to the internal allocator.
|
||||||
|
//!
|
||||||
|
//! <b>Throws</b>: Nothing
|
||||||
|
//!
|
||||||
|
//! <b>Complexity</b>: Constant.
|
||||||
|
//!
|
||||||
|
//! <b>Note</b>: Non-standard extension.
|
||||||
|
stored_allocator_type &get_stored_allocator() BOOST_CONTAINER_NOEXCEPT
|
||||||
|
{ return this->alloc(); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Returns the number of the elements contained in the vector.
|
//! <b>Effects</b>: Returns the number of the elements contained in the vector.
|
||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing.
|
//! <b>Throws</b>: Nothing.
|
||||||
@@ -855,7 +919,7 @@ class basic_string
|
|||||||
this->throw_length_error();
|
this->throw_length_error();
|
||||||
|
|
||||||
if (this->capacity() < res_arg){
|
if (this->capacity() < res_arg){
|
||||||
size_type n = containers_detail::max_value(res_arg, this->size()) + 1;
|
size_type n = container_detail::max_value(res_arg, this->size()) + 1;
|
||||||
size_type new_cap = this->next_capacity(n);
|
size_type new_cap = this->next_capacity(n);
|
||||||
pointer new_start = this->allocation_command
|
pointer new_start = this->allocation_command
|
||||||
(allocate_new, n, new_cap, new_cap).first;
|
(allocate_new, n, new_cap, new_cap).first;
|
||||||
@@ -912,8 +976,8 @@ class basic_string
|
|||||||
size_type long_storage = this->priv_long_storage();
|
size_type long_storage = this->priv_long_storage();
|
||||||
size_type long_size = this->priv_long_size();
|
size_type long_size = this->priv_long_size();
|
||||||
//Shrink from allocated buffer to the internal one, including trailing null
|
//Shrink from allocated buffer to the internal one, including trailing null
|
||||||
Traits::copy( containers_detail::get_pointer(this->priv_short_addr())
|
Traits::copy( container_detail::to_raw_pointer(this->priv_short_addr())
|
||||||
, containers_detail::get_pointer(long_addr)
|
, container_detail::to_raw_pointer(long_addr)
|
||||||
, long_size+1);
|
, long_size+1);
|
||||||
this->is_short(true);
|
this->is_short(true);
|
||||||
this->alloc().deallocate(long_addr, long_storage);
|
this->alloc().deallocate(long_addr, long_storage);
|
||||||
@@ -1020,7 +1084,7 @@ class basic_string
|
|||||||
if (pos > s.size())
|
if (pos > s.size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
return this->append(s.begin() + pos,
|
return this->append(s.begin() + pos,
|
||||||
s.begin() + pos + containers_detail::min_value(n, s.size() - pos));
|
s.begin() + pos + container_detail::min_value(n, s.size() - pos));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Requires</b>: s points to an array of at least n elements of CharT.
|
//! <b>Requires</b>: s points to an array of at least n elements of CharT.
|
||||||
@@ -1087,7 +1151,7 @@ class basic_string
|
|||||||
//!
|
//!
|
||||||
//! <b>Returns</b>: *this
|
//! <b>Returns</b>: *this
|
||||||
basic_string& assign(BOOST_RV_REF(basic_string) ms)
|
basic_string& assign(BOOST_RV_REF(basic_string) ms)
|
||||||
{ return this->swap(ms), *this; }
|
{ return this->swap_data(ms), *this; }
|
||||||
|
|
||||||
//! <b>Requires</b>: pos <= str.size()
|
//! <b>Requires</b>: pos <= str.size()
|
||||||
//!
|
//!
|
||||||
@@ -1102,7 +1166,7 @@ class basic_string
|
|||||||
if (pos > s.size())
|
if (pos > s.size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
return this->assign(s.begin() + pos,
|
return this->assign(s.begin() + pos,
|
||||||
s.begin() + pos + containers_detail::min_value(n, s.size() - pos));
|
s.begin() + pos + container_detail::min_value(n, s.size() - pos));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Requires</b>: s points to an array of at least n elements of CharT.
|
//! <b>Requires</b>: s points to an array of at least n elements of CharT.
|
||||||
@@ -1137,8 +1201,8 @@ class basic_string
|
|||||||
basic_string& assign(InputIter first, InputIter last)
|
basic_string& assign(InputIter first, InputIter last)
|
||||||
{
|
{
|
||||||
//Dispatch depending on integer/iterator
|
//Dispatch depending on integer/iterator
|
||||||
const bool aux_boolean = containers_detail::is_convertible<InputIter, size_type>::value;
|
const bool aux_boolean = container_detail::is_convertible<InputIter, size_type>::value;
|
||||||
typedef containers_detail::bool_<aux_boolean> Result;
|
typedef container_detail::bool_<aux_boolean> Result;
|
||||||
return this->priv_assign_dispatch(first, last, Result());
|
return this->priv_assign_dispatch(first, last, Result());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1172,10 +1236,10 @@ class basic_string
|
|||||||
{
|
{
|
||||||
if (pos1 > this->size() || pos2 > s.size())
|
if (pos1 > this->size() || pos2 > s.size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
size_type len = containers_detail::min_value(n, s.size() - pos2);
|
size_type len = container_detail::min_value(n, s.size() - pos2);
|
||||||
if (this->size() > this->max_size() - len)
|
if (this->size() > this->max_size() - len)
|
||||||
this->throw_length_error();
|
this->throw_length_error();
|
||||||
const CharT *beg_ptr = containers_detail::get_pointer(s.begin()) + pos2;
|
const CharT *beg_ptr = container_detail::to_raw_pointer(s.begin()) + pos2;
|
||||||
const CharT *end_ptr = beg_ptr + len;
|
const CharT *end_ptr = beg_ptr + len;
|
||||||
this->insert(this->priv_addr() + pos1, beg_ptr, end_ptr);
|
this->insert(this->priv_addr() + pos1, beg_ptr, end_ptr);
|
||||||
return *this;
|
return *this;
|
||||||
@@ -1271,8 +1335,8 @@ class basic_string
|
|||||||
void insert(const_iterator p, InputIter first, InputIter last)
|
void insert(const_iterator p, InputIter first, InputIter last)
|
||||||
{
|
{
|
||||||
//Dispatch depending on integer/iterator
|
//Dispatch depending on integer/iterator
|
||||||
const bool aux_boolean = containers_detail::is_convertible<InputIter, size_type>::value;
|
const bool aux_boolean = container_detail::is_convertible<InputIter, size_type>::value;
|
||||||
typedef containers_detail::bool_<aux_boolean> Result;
|
typedef container_detail::bool_<aux_boolean> Result;
|
||||||
this->priv_insert_dispatch(p, first, last, Result());
|
this->priv_insert_dispatch(p, first, last, Result());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1291,7 +1355,7 @@ class basic_string
|
|||||||
{
|
{
|
||||||
if (pos > size())
|
if (pos > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
erase(this->priv_addr() + pos, this->priv_addr() + pos + containers_detail::min_value(n, size() - pos));
|
erase(this->priv_addr() + pos, this->priv_addr() + pos + container_detail::min_value(n, size() - pos));
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1304,9 +1368,9 @@ class basic_string
|
|||||||
iterator erase(const_iterator p)
|
iterator erase(const_iterator p)
|
||||||
{
|
{
|
||||||
// The move includes the terminating null.
|
// The move includes the terminating null.
|
||||||
CharT *ptr = const_cast<CharT*>(containers_detail::get_pointer(p));
|
CharT *ptr = const_cast<CharT*>(container_detail::to_raw_pointer(p));
|
||||||
Traits::move(ptr,
|
Traits::move(ptr,
|
||||||
containers_detail::get_pointer(p + 1),
|
container_detail::to_raw_pointer(p + 1),
|
||||||
this->priv_size() - (p - this->priv_addr()));
|
this->priv_size() - (p - this->priv_addr()));
|
||||||
this->priv_size(this->priv_size()-1);
|
this->priv_size(this->priv_size()-1);
|
||||||
return iterator(ptr);
|
return iterator(ptr);
|
||||||
@@ -1322,11 +1386,11 @@ class basic_string
|
|||||||
//! the other elements being erased. If no such element exists, end() is returned.
|
//! the other elements being erased. If no such element exists, end() is returned.
|
||||||
iterator erase(const_iterator first, const_iterator last)
|
iterator erase(const_iterator first, const_iterator last)
|
||||||
{
|
{
|
||||||
CharT * f = const_cast<CharT*>(containers_detail::get_pointer(first));
|
CharT * f = const_cast<CharT*>(container_detail::to_raw_pointer(first));
|
||||||
if (first != last) { // The move includes the terminating null.
|
if (first != last) { // The move includes the terminating null.
|
||||||
size_type num_erased = last - first;
|
size_type num_erased = last - first;
|
||||||
Traits::move(f,
|
Traits::move(f,
|
||||||
containers_detail::get_pointer(last),
|
container_detail::to_raw_pointer(last),
|
||||||
(this->priv_size() + 1)-(last - this->priv_addr()));
|
(this->priv_size() + 1)-(last - this->priv_addr()));
|
||||||
size_type new_length = this->priv_size() - num_erased;
|
size_type new_length = this->priv_size() - num_erased;
|
||||||
this->priv_size(new_length);
|
this->priv_size(new_length);
|
||||||
@@ -1356,7 +1420,7 @@ class basic_string
|
|||||||
{
|
{
|
||||||
if (pos1 > size())
|
if (pos1 > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
const size_type len = containers_detail::min_value(n1, size() - pos1);
|
const size_type len = container_detail::min_value(n1, size() - pos1);
|
||||||
if (this->size() - len >= this->max_size() - str.size())
|
if (this->size() - len >= this->max_size() - str.size())
|
||||||
this->throw_length_error();
|
this->throw_length_error();
|
||||||
return this->replace(this->priv_addr() + pos1, this->priv_addr() + pos1 + len,
|
return this->replace(this->priv_addr() + pos1, this->priv_addr() + pos1 + len,
|
||||||
@@ -1377,8 +1441,8 @@ class basic_string
|
|||||||
{
|
{
|
||||||
if (pos1 > size() || pos2 > str.size())
|
if (pos1 > size() || pos2 > str.size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
const size_type len1 = containers_detail::min_value(n1, size() - pos1);
|
const size_type len1 = container_detail::min_value(n1, size() - pos1);
|
||||||
const size_type len2 = containers_detail::min_value(n2, str.size() - pos2);
|
const size_type len2 = container_detail::min_value(n2, str.size() - pos2);
|
||||||
if (this->size() - len1 >= this->max_size() - len2)
|
if (this->size() - len1 >= this->max_size() - len2)
|
||||||
this->throw_length_error();
|
this->throw_length_error();
|
||||||
return this->replace(this->priv_addr() + pos1, this->priv_addr() + pos1 + len1,
|
return this->replace(this->priv_addr() + pos1, this->priv_addr() + pos1 + len1,
|
||||||
@@ -1404,7 +1468,7 @@ class basic_string
|
|||||||
{
|
{
|
||||||
if (pos1 > size())
|
if (pos1 > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
const size_type len = containers_detail::min_value(n1, size() - pos1);
|
const size_type len = container_detail::min_value(n1, size() - pos1);
|
||||||
if (n2 > this->max_size() || size() - len >= this->max_size() - n2)
|
if (n2 > this->max_size() || size() - len >= this->max_size() - n2)
|
||||||
this->throw_length_error();
|
this->throw_length_error();
|
||||||
return this->replace(this->priv_addr() + pos1, this->priv_addr() + pos1 + len,
|
return this->replace(this->priv_addr() + pos1, this->priv_addr() + pos1 + len,
|
||||||
@@ -1429,7 +1493,7 @@ class basic_string
|
|||||||
{
|
{
|
||||||
if (pos > size())
|
if (pos > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
const size_type len = containers_detail::min_value(n1, size() - pos);
|
const size_type len = container_detail::min_value(n1, size() - pos);
|
||||||
const size_type n2 = Traits::length(s);
|
const size_type n2 = Traits::length(s);
|
||||||
if (n2 > this->max_size() || size() - len >= this->max_size() - n2)
|
if (n2 > this->max_size() || size() - len >= this->max_size() - n2)
|
||||||
this->throw_length_error();
|
this->throw_length_error();
|
||||||
@@ -1449,7 +1513,7 @@ class basic_string
|
|||||||
{
|
{
|
||||||
if (pos1 > size())
|
if (pos1 > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
const size_type len = containers_detail::min_value(n1, size() - pos1);
|
const size_type len = container_detail::min_value(n1, size() - pos1);
|
||||||
if (n2 > this->max_size() || size() - len >= this->max_size() - n2)
|
if (n2 > this->max_size() || size() - len >= this->max_size() - n2)
|
||||||
this->throw_length_error();
|
this->throw_length_error();
|
||||||
return this->replace(this->priv_addr() + pos1, this->priv_addr() + pos1 + len, n2, c);
|
return this->replace(this->priv_addr() + pos1, this->priv_addr() + pos1 + len, n2, c);
|
||||||
@@ -1498,11 +1562,11 @@ class basic_string
|
|||||||
{
|
{
|
||||||
const size_type len = static_cast<size_type>(i2 - i1);
|
const size_type len = static_cast<size_type>(i2 - i1);
|
||||||
if (len >= n) {
|
if (len >= n) {
|
||||||
Traits::assign(const_cast<CharT*>(containers_detail::get_pointer(i1)), n, c);
|
Traits::assign(const_cast<CharT*>(container_detail::to_raw_pointer(i1)), n, c);
|
||||||
erase(i1 + n, i2);
|
erase(i1 + n, i2);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
Traits::assign(const_cast<CharT*>(containers_detail::get_pointer(i1)), len, c);
|
Traits::assign(const_cast<CharT*>(container_detail::to_raw_pointer(i1)), len, c);
|
||||||
insert(i2, n - len, c);
|
insert(i2, n - len, c);
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
@@ -1519,8 +1583,8 @@ class basic_string
|
|||||||
basic_string& replace(const_iterator i1, const_iterator i2, InputIter j1, InputIter j2)
|
basic_string& replace(const_iterator i1, const_iterator i2, InputIter j1, InputIter j2)
|
||||||
{
|
{
|
||||||
//Dispatch depending on integer/iterator
|
//Dispatch depending on integer/iterator
|
||||||
const bool aux_boolean = containers_detail::is_convertible<InputIter, size_type>::value;
|
const bool aux_boolean = container_detail::is_convertible<InputIter, size_type>::value;
|
||||||
typedef containers_detail::bool_<aux_boolean> Result;
|
typedef container_detail::bool_<aux_boolean> Result;
|
||||||
return this->priv_replace_dispatch(i1, i2, j1, j2, Result());
|
return this->priv_replace_dispatch(i1, i2, j1, j2, Result());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1539,8 +1603,8 @@ class basic_string
|
|||||||
{
|
{
|
||||||
if (pos > size())
|
if (pos > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
const size_type len = containers_detail::min_value(n, size() - pos);
|
const size_type len = container_detail::min_value(n, size() - pos);
|
||||||
Traits::copy(s, containers_detail::get_pointer(this->priv_addr() + pos), len);
|
Traits::copy(s, container_detail::to_raw_pointer(this->priv_addr() + pos), len);
|
||||||
return len;
|
return len;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1549,7 +1613,11 @@ class basic_string
|
|||||||
//!
|
//!
|
||||||
//! <b>Throws</b>: Nothing
|
//! <b>Throws</b>: Nothing
|
||||||
void swap(basic_string& x)
|
void swap(basic_string& x)
|
||||||
{ base_t::swap(x); }
|
{
|
||||||
|
this->base_t::swap_data(x);
|
||||||
|
container_detail::bool_<allocator_traits_type::propagate_on_container_swap::value> flag;
|
||||||
|
container_detail::swap_alloc(this->alloc(), x.alloc(), flag);
|
||||||
|
}
|
||||||
|
|
||||||
//! <b>Requires</b>: The program shall not alter any of the values stored in the character array.
|
//! <b>Requires</b>: The program shall not alter any of the values stored in the character array.
|
||||||
//!
|
//!
|
||||||
@@ -1557,7 +1625,7 @@ class basic_string
|
|||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: constant time.
|
//! <b>Complexity</b>: constant time.
|
||||||
const CharT* c_str() const
|
const CharT* c_str() const
|
||||||
{ return containers_detail::get_pointer(this->priv_addr()); }
|
{ return container_detail::to_raw_pointer(this->priv_addr()); }
|
||||||
|
|
||||||
//! <b>Requires</b>: The program shall not alter any of the values stored in the character array.
|
//! <b>Requires</b>: The program shall not alter any of the values stored in the character array.
|
||||||
//!
|
//!
|
||||||
@@ -1565,7 +1633,7 @@ class basic_string
|
|||||||
//!
|
//!
|
||||||
//! <b>Complexity</b>: constant time.
|
//! <b>Complexity</b>: constant time.
|
||||||
const CharT* data() const
|
const CharT* data() const
|
||||||
{ return containers_detail::get_pointer(this->priv_addr()); }
|
{ return container_detail::to_raw_pointer(this->priv_addr()); }
|
||||||
|
|
||||||
//! <b>Effects</b>: Determines the lowest position xpos, if possible, such that both
|
//! <b>Effects</b>: Determines the lowest position xpos, if possible, such that both
|
||||||
//! of the following conditions obtain: 19 pos <= xpos and xpos + str.size() <= size();
|
//! of the following conditions obtain: 19 pos <= xpos and xpos + str.size() <= size();
|
||||||
@@ -1589,8 +1657,8 @@ class basic_string
|
|||||||
else {
|
else {
|
||||||
pointer finish = this->priv_addr() + this->priv_size();
|
pointer finish = this->priv_addr() + this->priv_size();
|
||||||
const const_iterator result =
|
const const_iterator result =
|
||||||
std::search(containers_detail::get_pointer(this->priv_addr() + pos),
|
std::search(container_detail::to_raw_pointer(this->priv_addr() + pos),
|
||||||
containers_detail::get_pointer(finish),
|
container_detail::to_raw_pointer(finish),
|
||||||
s, s + n, Eq_traits<Traits>());
|
s, s + n, Eq_traits<Traits>());
|
||||||
return result != finish ? result - begin() : npos;
|
return result != finish ? result - begin() : npos;
|
||||||
}
|
}
|
||||||
@@ -1643,9 +1711,9 @@ class basic_string
|
|||||||
if (n > len)
|
if (n > len)
|
||||||
return npos;
|
return npos;
|
||||||
else if (n == 0)
|
else if (n == 0)
|
||||||
return containers_detail::min_value(len, pos);
|
return container_detail::min_value(len, pos);
|
||||||
else {
|
else {
|
||||||
const const_iterator last = begin() + containers_detail::min_value(len - n, pos) + n;
|
const const_iterator last = begin() + container_detail::min_value(len - n, pos) + n;
|
||||||
const const_iterator result = find_end(begin(), last,
|
const const_iterator result = find_end(begin(), last,
|
||||||
s, s + n,
|
s, s + n,
|
||||||
Eq_traits<Traits>());
|
Eq_traits<Traits>());
|
||||||
@@ -1672,7 +1740,7 @@ class basic_string
|
|||||||
if (len < 1)
|
if (len < 1)
|
||||||
return npos;
|
return npos;
|
||||||
else {
|
else {
|
||||||
const const_iterator last = begin() + containers_detail::min_value(len - 1, pos) + 1;
|
const const_iterator last = begin() + container_detail::min_value(len - 1, pos) + 1;
|
||||||
const_reverse_iterator rresult =
|
const_reverse_iterator rresult =
|
||||||
std::find_if(const_reverse_iterator(last), rend(),
|
std::find_if(const_reverse_iterator(last), rend(),
|
||||||
std::bind2nd(Eq_traits<Traits>(), c));
|
std::bind2nd(Eq_traits<Traits>(), c));
|
||||||
@@ -1746,7 +1814,7 @@ class basic_string
|
|||||||
if (len < 1)
|
if (len < 1)
|
||||||
return npos;
|
return npos;
|
||||||
else {
|
else {
|
||||||
const const_iterator last = this->priv_addr() + containers_detail::min_value(len - 1, pos) + 1;
|
const const_iterator last = this->priv_addr() + container_detail::min_value(len - 1, pos) + 1;
|
||||||
const const_reverse_iterator rresult =
|
const const_reverse_iterator rresult =
|
||||||
std::find_first_of(const_reverse_iterator(last), rend(),
|
std::find_first_of(const_reverse_iterator(last), rend(),
|
||||||
s, s + n,
|
s, s + n,
|
||||||
@@ -1843,7 +1911,7 @@ class basic_string
|
|||||||
if (len < 1)
|
if (len < 1)
|
||||||
return npos;
|
return npos;
|
||||||
else {
|
else {
|
||||||
const const_iterator last = begin() + containers_detail::min_value(len - 1, pos) + 1;
|
const const_iterator last = begin() + container_detail::min_value(len - 1, pos) + 1;
|
||||||
const const_reverse_iterator rresult =
|
const const_reverse_iterator rresult =
|
||||||
std::find_if(const_reverse_iterator(last), rend(),
|
std::find_if(const_reverse_iterator(last), rend(),
|
||||||
Not_within_traits<Traits>(s, s + n));
|
Not_within_traits<Traits>(s, s + n));
|
||||||
@@ -1869,7 +1937,7 @@ class basic_string
|
|||||||
if (len < 1)
|
if (len < 1)
|
||||||
return npos;
|
return npos;
|
||||||
else {
|
else {
|
||||||
const const_iterator last = begin() + containers_detail::min_value(len - 1, pos) + 1;
|
const const_iterator last = begin() + container_detail::min_value(len - 1, pos) + 1;
|
||||||
const_reverse_iterator rresult =
|
const_reverse_iterator rresult =
|
||||||
std::find_if(const_reverse_iterator(last), rend(),
|
std::find_if(const_reverse_iterator(last), rend(),
|
||||||
std::not1(std::bind2nd(Eq_traits<Traits>(), c)));
|
std::not1(std::bind2nd(Eq_traits<Traits>(), c)));
|
||||||
@@ -1890,7 +1958,7 @@ class basic_string
|
|||||||
if (pos > size())
|
if (pos > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
return basic_string(this->priv_addr() + pos,
|
return basic_string(this->priv_addr() + pos,
|
||||||
this->priv_addr() + pos + containers_detail::min_value(n, size() - pos), this->alloc());
|
this->priv_addr() + pos + container_detail::min_value(n, size() - pos), this->alloc());
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Effects</b>: Determines the effective length rlen of the string to copy as
|
//! <b>Effects</b>: Determines the effective length rlen of the string to copy as
|
||||||
@@ -1918,7 +1986,7 @@ class basic_string
|
|||||||
if (pos1 > size())
|
if (pos1 > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
return s_compare(this->priv_addr() + pos1,
|
return s_compare(this->priv_addr() + pos1,
|
||||||
this->priv_addr() + pos1 + containers_detail::min_value(n1, size() - pos1),
|
this->priv_addr() + pos1 + container_detail::min_value(n1, size() - pos1),
|
||||||
str.priv_addr(), str.priv_addr() + str.priv_size());
|
str.priv_addr(), str.priv_addr() + str.priv_size());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1935,9 +2003,9 @@ class basic_string
|
|||||||
if (pos1 > size() || pos2 > str.size())
|
if (pos1 > size() || pos2 > str.size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
return s_compare(this->priv_addr() + pos1,
|
return s_compare(this->priv_addr() + pos1,
|
||||||
this->priv_addr() + pos1 + containers_detail::min_value(n1, size() - pos1),
|
this->priv_addr() + pos1 + container_detail::min_value(n1, size() - pos1),
|
||||||
str.priv_addr() + pos2,
|
str.priv_addr() + pos2,
|
||||||
str.priv_addr() + pos2 + containers_detail::min_value(n2, size() - pos2));
|
str.priv_addr() + pos2 + container_detail::min_value(n2, size() - pos2));
|
||||||
}
|
}
|
||||||
|
|
||||||
//! <b>Throws</b>: Nothing
|
//! <b>Throws</b>: Nothing
|
||||||
@@ -1958,7 +2026,7 @@ class basic_string
|
|||||||
if (pos1 > size())
|
if (pos1 > size())
|
||||||
this->throw_out_of_range();
|
this->throw_out_of_range();
|
||||||
return s_compare(this->priv_addr() + pos1,
|
return s_compare(this->priv_addr() + pos1,
|
||||||
this->priv_addr() + pos1 + containers_detail::min_value(n1, size() - pos1),
|
this->priv_addr() + pos1 + container_detail::min_value(n1, size() - pos1),
|
||||||
s, s + n2);
|
s, s + n2);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1977,13 +2045,16 @@ class basic_string
|
|||||||
{
|
{
|
||||||
const difference_type n1 = l1 - f1;
|
const difference_type n1 = l1 - f1;
|
||||||
const difference_type n2 = l2 - f2;
|
const difference_type n2 = l2 - f2;
|
||||||
const int cmp = Traits::compare(containers_detail::get_pointer(f1),
|
const int cmp = Traits::compare(container_detail::to_raw_pointer(f1),
|
||||||
containers_detail::get_pointer(f2),
|
container_detail::to_raw_pointer(f2),
|
||||||
containers_detail::min_value(n1, n2));
|
container_detail::min_value(n1, n2));
|
||||||
return cmp != 0 ? cmp : (n1 < n2 ? -1 : (n1 > n2 ? 1 : 0));
|
return cmp != 0 ? cmp : (n1 < n2 ? -1 : (n1 > n2 ? 1 : 0));
|
||||||
}
|
}
|
||||||
|
|
||||||
void priv_shrink_to_fit_dynamic_buffer(allocator_v1)
|
template<class AllocVersion>
|
||||||
|
void priv_shrink_to_fit_dynamic_buffer
|
||||||
|
( AllocVersion
|
||||||
|
, typename container_detail::enable_if<container_detail::is_same<AllocVersion, allocator_v1> >::type* = 0)
|
||||||
{
|
{
|
||||||
//Allocate a new buffer.
|
//Allocate a new buffer.
|
||||||
size_type real_cap = 0;
|
size_type real_cap = 0;
|
||||||
@@ -1995,8 +2066,8 @@ class basic_string
|
|||||||
std::pair<pointer, bool> ret = this->allocation_command
|
std::pair<pointer, bool> ret = this->allocation_command
|
||||||
(allocate_new, long_size+1, long_size+1, real_cap, long_addr);
|
(allocate_new, long_size+1, long_size+1, real_cap, long_addr);
|
||||||
//Copy and update
|
//Copy and update
|
||||||
Traits::copy( containers_detail::get_pointer(ret.first)
|
Traits::copy( container_detail::to_raw_pointer(ret.first)
|
||||||
, containers_detail::get_pointer(this->priv_long_addr())
|
, container_detail::to_raw_pointer(this->priv_long_addr())
|
||||||
, long_size+1);
|
, long_size+1);
|
||||||
this->priv_long_addr(ret.first);
|
this->priv_long_addr(ret.first);
|
||||||
this->priv_storage(real_cap);
|
this->priv_storage(real_cap);
|
||||||
@@ -2008,7 +2079,10 @@ class basic_string
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void priv_shrink_to_fit_dynamic_buffer(allocator_v2)
|
template<class AllocVersion>
|
||||||
|
void priv_shrink_to_fit_dynamic_buffer
|
||||||
|
( AllocVersion
|
||||||
|
, typename container_detail::enable_if<container_detail::is_same<AllocVersion, allocator_v2> >::type* = 0)
|
||||||
{
|
{
|
||||||
size_type received_size;
|
size_type received_size;
|
||||||
if(this->alloc().allocation_command
|
if(this->alloc().allocation_command
|
||||||
@@ -2044,7 +2118,7 @@ class basic_string
|
|||||||
std::forward_iterator_tag)
|
std::forward_iterator_tag)
|
||||||
{
|
{
|
||||||
difference_type n = std::distance(f, l);
|
difference_type n = std::distance(f, l);
|
||||||
this->allocate_initial_block(containers_detail::max_value<difference_type>(n+1, InternalBufferChars));
|
this->allocate_initial_block(container_detail::max_value<difference_type>(n+1, InternalBufferChars));
|
||||||
priv_uninitialized_copy(f, l, this->priv_addr());
|
priv_uninitialized_copy(f, l, this->priv_addr());
|
||||||
this->priv_size(n);
|
this->priv_size(n);
|
||||||
this->priv_terminate_string();
|
this->priv_terminate_string();
|
||||||
@@ -2058,16 +2132,16 @@ class basic_string
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <class Integer>
|
template <class Integer>
|
||||||
void priv_initialize_dispatch(Integer n, Integer x, containers_detail::true_)
|
void priv_initialize_dispatch(Integer n, Integer x, container_detail::true_)
|
||||||
{
|
{
|
||||||
this->allocate_initial_block(containers_detail::max_value<difference_type>(n+1, InternalBufferChars));
|
this->allocate_initial_block(container_detail::max_value<difference_type>(n+1, InternalBufferChars));
|
||||||
priv_uninitialized_fill_n(this->priv_addr(), n, x);
|
priv_uninitialized_fill_n(this->priv_addr(), n, x);
|
||||||
this->priv_size(n);
|
this->priv_size(n);
|
||||||
this->priv_terminate_string();
|
this->priv_terminate_string();
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class InputIter>
|
template <class InputIter>
|
||||||
void priv_initialize_dispatch(InputIter f, InputIter l, containers_detail::false_)
|
void priv_initialize_dispatch(InputIter f, InputIter l, container_detail::false_)
|
||||||
{ this->priv_range_initialize(f, l); }
|
{ this->priv_range_initialize(f, l); }
|
||||||
|
|
||||||
template<class FwdIt, class Count> inline
|
template<class FwdIt, class Count> inline
|
||||||
@@ -2117,15 +2191,15 @@ class basic_string
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <class Integer>
|
template <class Integer>
|
||||||
basic_string& priv_assign_dispatch(Integer n, Integer x, containers_detail::true_)
|
basic_string& priv_assign_dispatch(Integer n, Integer x, container_detail::true_)
|
||||||
{ return this->assign((size_type) n, (CharT) x); }
|
{ return this->assign((size_type) n, (CharT) x); }
|
||||||
|
|
||||||
template <class InputIter>
|
template <class InputIter>
|
||||||
basic_string& priv_assign_dispatch(InputIter f, InputIter l,
|
basic_string& priv_assign_dispatch(InputIter f, InputIter l,
|
||||||
containers_detail::false_)
|
container_detail::false_)
|
||||||
{
|
{
|
||||||
size_type cur = 0;
|
size_type cur = 0;
|
||||||
CharT *ptr = containers_detail::get_pointer(this->priv_addr());
|
CharT *ptr = container_detail::to_raw_pointer(this->priv_addr());
|
||||||
while (f != l && cur != this->priv_size()) {
|
while (f != l && cur != this->priv_size()) {
|
||||||
Traits::assign(*ptr, *f);
|
Traits::assign(*ptr, *f);
|
||||||
++f;
|
++f;
|
||||||
@@ -2189,10 +2263,10 @@ class basic_string
|
|||||||
pointer_past_last, pointer_past_last);
|
pointer_past_last, pointer_past_last);
|
||||||
|
|
||||||
this->priv_size(this->priv_size()+n);
|
this->priv_size(this->priv_size()+n);
|
||||||
Traits::move(const_cast<CharT*>(containers_detail::get_pointer(position + n)),
|
Traits::move(const_cast<CharT*>(container_detail::to_raw_pointer(position + n)),
|
||||||
containers_detail::get_pointer(position),
|
container_detail::to_raw_pointer(position),
|
||||||
(elems_after - n) + 1);
|
(elems_after - n) + 1);
|
||||||
this->priv_copy(first, last, const_cast<CharT*>(containers_detail::get_pointer(position)));
|
this->priv_copy(first, last, const_cast<CharT*>(container_detail::to_raw_pointer(position)));
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
ForwardIter mid = first;
|
ForwardIter mid = first;
|
||||||
@@ -2204,7 +2278,7 @@ class basic_string
|
|||||||
(position, const_iterator(this->priv_addr() + old_length + 1),
|
(position, const_iterator(this->priv_addr() + old_length + 1),
|
||||||
this->priv_addr() + this->priv_size());
|
this->priv_addr() + this->priv_size());
|
||||||
this->priv_size(this->priv_size() + elems_after);
|
this->priv_size(this->priv_size() + elems_after);
|
||||||
this->priv_copy(first, mid, const_cast<CharT*>(containers_detail::get_pointer(position)));
|
this->priv_copy(first, mid, const_cast<CharT*>(container_detail::to_raw_pointer(position)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
@@ -2231,9 +2305,9 @@ class basic_string
|
|||||||
else{
|
else{
|
||||||
//value_type is POD, so backwards expansion is much easier
|
//value_type is POD, so backwards expansion is much easier
|
||||||
//than with vector<T>
|
//than with vector<T>
|
||||||
value_type *oldbuf = containers_detail::get_pointer(old_start);
|
value_type *oldbuf = container_detail::to_raw_pointer(old_start);
|
||||||
value_type *newbuf = containers_detail::get_pointer(new_start);
|
value_type *newbuf = container_detail::to_raw_pointer(new_start);
|
||||||
const value_type *pos = containers_detail::get_pointer(position);
|
const value_type *pos = container_detail::to_raw_pointer(position);
|
||||||
size_type before = pos - oldbuf;
|
size_type before = pos - oldbuf;
|
||||||
|
|
||||||
//First move old data
|
//First move old data
|
||||||
@@ -2253,12 +2327,12 @@ class basic_string
|
|||||||
|
|
||||||
template <class Integer>
|
template <class Integer>
|
||||||
void priv_insert_dispatch(const_iterator p, Integer n, Integer x,
|
void priv_insert_dispatch(const_iterator p, Integer n, Integer x,
|
||||||
containers_detail::true_)
|
container_detail::true_)
|
||||||
{ insert(p, (size_type) n, (CharT) x); }
|
{ insert(p, (size_type) n, (CharT) x); }
|
||||||
|
|
||||||
template <class InputIter>
|
template <class InputIter>
|
||||||
void priv_insert_dispatch(const_iterator p, InputIter first, InputIter last,
|
void priv_insert_dispatch(const_iterator p, InputIter first, InputIter last,
|
||||||
containers_detail::false_)
|
container_detail::false_)
|
||||||
{
|
{
|
||||||
typedef typename std::iterator_traits<InputIter>::iterator_category Category;
|
typedef typename std::iterator_traits<InputIter>::iterator_category Category;
|
||||||
priv_insert(p, first, last, Category());
|
priv_insert(p, first, last, Category());
|
||||||
@@ -2277,13 +2351,13 @@ class basic_string
|
|||||||
template <class Integer>
|
template <class Integer>
|
||||||
basic_string& priv_replace_dispatch(const_iterator first, const_iterator last,
|
basic_string& priv_replace_dispatch(const_iterator first, const_iterator last,
|
||||||
Integer n, Integer x,
|
Integer n, Integer x,
|
||||||
containers_detail::true_)
|
container_detail::true_)
|
||||||
{ return this->replace(first, last, (size_type) n, (CharT) x); }
|
{ return this->replace(first, last, (size_type) n, (CharT) x); }
|
||||||
|
|
||||||
template <class InputIter>
|
template <class InputIter>
|
||||||
basic_string& priv_replace_dispatch(const_iterator first, const_iterator last,
|
basic_string& priv_replace_dispatch(const_iterator first, const_iterator last,
|
||||||
InputIter f, InputIter l,
|
InputIter f, InputIter l,
|
||||||
containers_detail::false_)
|
container_detail::false_)
|
||||||
{
|
{
|
||||||
typedef typename std::iterator_traits<InputIter>::iterator_category Category;
|
typedef typename std::iterator_traits<InputIter>::iterator_category Category;
|
||||||
return this->priv_replace(first, last, f, l, Category());
|
return this->priv_replace(first, last, f, l, Category());
|
||||||
@@ -2312,13 +2386,13 @@ class basic_string
|
|||||||
difference_type n = std::distance(f, l);
|
difference_type n = std::distance(f, l);
|
||||||
const difference_type len = last - first;
|
const difference_type len = last - first;
|
||||||
if (len >= n) {
|
if (len >= n) {
|
||||||
this->priv_copy(f, l, const_cast<CharT*>(containers_detail::get_pointer(first)));
|
this->priv_copy(f, l, const_cast<CharT*>(container_detail::to_raw_pointer(first)));
|
||||||
this->erase(first + n, last);
|
this->erase(first + n, last);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
ForwardIter m = f;
|
ForwardIter m = f;
|
||||||
std::advance(m, len);
|
std::advance(m, len);
|
||||||
this->priv_copy(f, m, const_cast<CharT*>(containers_detail::get_pointer(first)));
|
this->priv_copy(f, m, const_cast<CharT*>(container_detail::to_raw_pointer(first)));
|
||||||
this->insert(last, m, l);
|
this->insert(last, m, l);
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
@@ -2364,10 +2438,20 @@ operator+(const basic_string<CharT,Traits,A>& x,
|
|||||||
typedef basic_string<CharT,Traits,A> str_t;
|
typedef basic_string<CharT,Traits,A> str_t;
|
||||||
typedef typename str_t::reserve_t reserve_t;
|
typedef typename str_t::reserve_t reserve_t;
|
||||||
reserve_t reserve;
|
reserve_t reserve;
|
||||||
str_t result(reserve, x.size() + y.size(), x.alloc());
|
str_t result(reserve, x.size() + y.size(), x.get_stored_allocator());
|
||||||
result.append(x);
|
result.append(x);
|
||||||
result.append(y);
|
result.append(y);
|
||||||
return result;
|
return boost::move(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class CharT, class Traits, class A> inline
|
||||||
|
BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A)
|
||||||
|
operator+(
|
||||||
|
BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A) mx
|
||||||
|
, BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A) my)
|
||||||
|
{
|
||||||
|
mx += my;
|
||||||
|
return boost::move(mx);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class CharT, class Traits, class A> inline
|
template <class CharT, class Traits, class A> inline
|
||||||
@@ -2386,7 +2470,8 @@ BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A)
|
|||||||
BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A) my)
|
BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A) my)
|
||||||
{
|
{
|
||||||
typedef typename basic_string<CharT,Traits,A>::size_type size_type;
|
typedef typename basic_string<CharT,Traits,A>::size_type size_type;
|
||||||
return my.replace(size_type(0), size_type(0), x);
|
my.replace(size_type(0), size_type(0), x);
|
||||||
|
return boost::move(my);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class CharT, class Traits, class A>
|
template <class CharT, class Traits, class A>
|
||||||
@@ -2400,7 +2485,7 @@ operator+(const CharT* s, const basic_string<CharT,Traits,A>& y)
|
|||||||
str_t result(reserve, n + y.size());
|
str_t result(reserve, n + y.size());
|
||||||
result.append(s, s + n);
|
result.append(s, s + n);
|
||||||
result.append(y);
|
result.append(y);
|
||||||
return result;
|
return boost::move(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class CharT, class Traits, class A> inline
|
template <class CharT, class Traits, class A> inline
|
||||||
@@ -2409,7 +2494,7 @@ operator+(const CharT* s,
|
|||||||
BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A) my)
|
BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A) my)
|
||||||
{
|
{
|
||||||
typedef typename basic_string<CharT,Traits,A>::size_type size_type;
|
typedef typename basic_string<CharT,Traits,A>::size_type size_type;
|
||||||
return boost::move(my.get().replace(size_type(0), size_type(0), s));
|
return boost::move(my.replace(size_type(0), size_type(0), s));
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class CharT, class Traits, class A>
|
template <class CharT, class Traits, class A>
|
||||||
@@ -2422,7 +2507,7 @@ operator+(CharT c, const basic_string<CharT,Traits,A>& y)
|
|||||||
str_t result(reserve, 1 + y.size());
|
str_t result(reserve, 1 + y.size());
|
||||||
result.push_back(c);
|
result.push_back(c);
|
||||||
result.append(y);
|
result.append(y);
|
||||||
return result;
|
return boost::move(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class CharT, class Traits, class A> inline
|
template <class CharT, class Traits, class A> inline
|
||||||
@@ -2431,7 +2516,7 @@ operator+(CharT c,
|
|||||||
BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A) my)
|
BOOST_RV_REF_3_TEMPL_ARGS(basic_string, CharT, Traits, A) my)
|
||||||
{
|
{
|
||||||
typedef typename basic_string<CharT,Traits,A>::size_type size_type;
|
typedef typename basic_string<CharT,Traits,A>::size_type size_type;
|
||||||
return my.replace(size_type(0), size_type(0), &c, &c + 1);
|
return boost::move(my.replace(size_type(0), size_type(0), &c, &c + 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class CharT, class Traits, class A>
|
template <class CharT, class Traits, class A>
|
||||||
@@ -2442,10 +2527,10 @@ operator+(const basic_string<CharT,Traits,A>& x, const CharT* s)
|
|||||||
typedef typename str_t::reserve_t reserve_t;
|
typedef typename str_t::reserve_t reserve_t;
|
||||||
reserve_t reserve;
|
reserve_t reserve;
|
||||||
const typename str_t::size_type n = Traits::length(s);
|
const typename str_t::size_type n = Traits::length(s);
|
||||||
str_t result(reserve, x.size() + n, x.alloc());
|
str_t result(reserve, x.size() + n, x.get_stored_allocator());
|
||||||
result.append(x);
|
result.append(x);
|
||||||
result.append(s, s + n);
|
result.append(s, s + n);
|
||||||
return result;
|
return boost::move(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class CharT, class Traits, class A>
|
template <class CharT, class Traits, class A>
|
||||||
@@ -2461,13 +2546,13 @@ template <class CharT, class Traits, class A>
|
|||||||
inline basic_string<CharT,Traits,A>
|
inline basic_string<CharT,Traits,A>
|
||||||
operator+(const basic_string<CharT,Traits,A>& x, const CharT c)
|
operator+(const basic_string<CharT,Traits,A>& x, const CharT c)
|
||||||
{
|
{
|
||||||
typedef basic_string<CharT,Traits,A> str_t;
|
typedef basic_string<CharT,Traits,A> str_t;
|
||||||
typedef typename str_t::reserve_t reserve_t;
|
typedef typename str_t::reserve_t reserve_t;
|
||||||
reserve_t reserve;
|
reserve_t reserve;
|
||||||
str_t result(reserve, x.size() + 1, x.alloc());
|
str_t result(reserve, x.size() + 1, x.get_stored_allocator());
|
||||||
result.append(x);
|
result.append(x);
|
||||||
result.push_back(c);
|
result.push_back(c);
|
||||||
return result;
|
return boost::move(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class CharT, class Traits, class A>
|
template <class CharT, class Traits, class A>
|
||||||
@@ -2616,7 +2701,7 @@ inline void swap(basic_string<CharT,Traits,A>& x, basic_string<CharT,Traits,A>&
|
|||||||
|
|
||||||
/// @cond
|
/// @cond
|
||||||
// I/O.
|
// I/O.
|
||||||
namespace containers_detail {
|
namespace container_detail {
|
||||||
|
|
||||||
template <class CharT, class Traits>
|
template <class CharT, class Traits>
|
||||||
inline bool
|
inline bool
|
||||||
@@ -2633,7 +2718,7 @@ string_fill(std::basic_ostream<CharT, Traits>& os,
|
|||||||
return ok;
|
return ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
} //namespace containers_detail {
|
} //namespace container_detail {
|
||||||
/// @endcond
|
/// @endcond
|
||||||
|
|
||||||
template <class CharT, class Traits, class A>
|
template <class CharT, class Traits, class A>
|
||||||
@@ -2655,13 +2740,13 @@ operator<<(std::basic_ostream<CharT, Traits>& os, const basic_string<CharT,Trait
|
|||||||
pad_len = w - n;
|
pad_len = w - n;
|
||||||
|
|
||||||
if (!left)
|
if (!left)
|
||||||
ok = containers_detail::string_fill(os, buf, pad_len);
|
ok = container_detail::string_fill(os, buf, pad_len);
|
||||||
|
|
||||||
ok = ok &&
|
ok = ok &&
|
||||||
buf->sputn(s.data(), std::streamsize(n)) == std::streamsize(n);
|
buf->sputn(s.data(), std::streamsize(n)) == std::streamsize(n);
|
||||||
|
|
||||||
if (left)
|
if (left)
|
||||||
ok = ok && containers_detail::string_fill(os, buf, pad_len);
|
ok = ok && container_detail::string_fill(os, buf, pad_len);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!ok)
|
if (!ok)
|
||||||
@@ -2783,4 +2868,4 @@ struct has_trivial_destructor_after_move<boost::container::basic_string<C, T, A>
|
|||||||
|
|
||||||
#include <boost/container/detail/config_end.hpp>
|
#include <boost/container/detail/config_end.hpp>
|
||||||
|
|
||||||
#endif // BOOST_CONTAINERS_STRING_HPP
|
#endif // BOOST_CONTAINER_STRING_HPP
|
||||||
|
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user