173 changes: 150 additions & 23 deletions doc/container.qbk
Expand Up @@ -49,9 +49,13 @@ In short, what does [*Boost.Container] offer?

[section:introduction_building_container Building Boost.Container]

There is no need to compile [*Boost.Container], since it's
a header only library. Just include your Boost header directory in your
compiler include path.
There is no need to compile [*Boost.Container] if you don't use [link container.extended_functionality.extended_allocators Extended Allocators]
since in that case it's a header-only library. Just include your Boost header directory in your compiler include path.

[link container.extended_functionality.extended_allocators Extended Allocators] are
implemented as a separately compiled library, so you must install binaries in a location that can be found by your linker
when using these classes. If you followed the [@http://www.boost.org/doc/libs/release/more/getting_started/index.html Boost Getting Started] instructions,
that's already been done for you.

[endsect]

Expand Down Expand Up @@ -148,12 +152,19 @@ today, in fact, implementors would have to go out of their way to prohibit it!]]
C++11 standard is also cautious about incomplete types and STL: ["['17.6.4.8 Other functions (...) 2.
the effects are undefined in the following cases: (...) In particular - if an incomplete type (3.9)
is used as a template argument when instantiating a template component,
unless specifically allowed for that component]]. Fortunately [*Boost.Container] containers are designed
to support type erasure and recursive types, so let's see some examples:
unless specifically allowed for that component]].

Fortunately all [*Boost.Container] containers except
[classref boost::container::static_vector static_vector] and
[classref boost::container::basic_string basic_string] are designed to support incomplete types.
[classref boost::container::static_vector static_vector] is special because
it statically allocates memory for `value_type` and this requires complete types and
[classref boost::container::basic_string basic_string] implements Small String Optimization which
also requires complete types.

[section:recursive_containers Recursive containers]

All containers offered by [*Boost.Container] can be used to define recursive containers:
Most [*Boost.Container] containers can be used to define recursive containers:

[import ../example/doc_recursive_containers.cpp]
[doc_recursive_containers]
Expand Down Expand Up @@ -261,8 +272,8 @@ When dealing with user-defined classes, (e.g. when constructing user-defined cla
propagate error situations internally as no error will be propagated through [*Boost.Container].
* If `BOOST_NO_EXCEPTIONS` is *not* defined, the library propagates exceptions offering the exception guarantees detailed in the documentation.

When the library needs to throw an exception (such as `out_of_range` when an incorrect index is used in `vector::at`)], the library calls
a throw callback declared in `<boost/container/throw_exception.hpp>`:
When the library needs to throw an exception (such as `out_of_range` when an incorrect index is used in `vector::at`), the library calls
a throw-callback declared in [headerref boost/container/throw_exception.hpp]:

* If `BOOST_CONTAINER_USER_DEFINED_THROW_CALLBACKS` is defined, then the programmer must provide its own definition for all
`throw_xxx` functions. Those functions can't return, they must throw an exception or call `std::exit` or `std::abort`.
Expand Down Expand Up @@ -522,6 +533,123 @@ using [@http://en.cppreference.com/w/cpp/language/default_initialization default

[endsect]

[section:ordered_range_insertion Ordered range insertion for associative containers (['ordered_unique_range], ['ordered_range]) ]

When filling associative containers big performance gains can be achieved if the input range to be inserted
is guaranteed by the user to be ordered according to the predicate. This can happen when inserting values from a `set` to
a `multiset` or between different associative container families (`[multi]set/map` vs. `flat_[multi]set/map`).

[*Boost.Container] has some overloads for constructors and insertions taking an `ordered_unique_range_t` or
an `ordered_range_t` tag parameters as the first argument. When an `ordered_unique_range_t` overload is used, the
user notifies the container that the input range is ordered according to the container predicate and has no
duplicates. When an `ordered_range_t` overload is used, the
user notifies the container that the input range is ordered according to the container predicate but it might
have duplicates. With this information, the container can avoid multiple predicate calls and improve insertion
times.

[endsect]

[section:constant_time_range_splice Constant-time range splice for `(s)list`]

In the first C++ standard `list::size()` was not required to be constant-time,
and that caused some controversy in the C++ community. Quoting Howard Hinnant's
[@http://home.roadrunner.com/~hinnant/On_list_size.html ['On List Size]] paper:

[: ['There is a considerable debate on whether `std::list<T>::size()` should be O(1) or O(N).
The usual argument notes that it is a tradeoff with:]

`splice(iterator position, list& x, iterator first, iterator last);`

['If size() is O(1) and this != &x, then this method must perform a linear operation so that it
can adjust the size member in each list]]

C++11 definitely required `size()` to be O(1), so range splice became O(N). However,
Howard Hinnant's paper proposed a new `splice` overload so that even O(1) `list:size()`
implementations could achieve O(1) range splice when the range size was known to the caller:

[: `void splice(iterator position, list& x, iterator first, iterator last, size_type n);`

[*Effects]: Inserts elements in the range [first, last) before position and removes the elements from x.

[*Requires]: [first, last) is a valid range in x. The result is undefined if position is an iterator in the range [first, last). Invalidates only the iterators and references to the spliced elements. n == distance(first, last).

[*Throws]: Nothing.

[*Complexity]: Constant time.
]

This new splice signature allows the client to pass the distance of the input range in.
This information is often available at the call site. If it is passed in,
then the operation is constant time, even with an O(1) size.

[*Boost.Container] implements this overload for `list` and a modified version of it for `slist`
(as `slist::size()` is also `O(1)`).

[endsect]

[section:extended_allocators Extended allocators]

Many C++ programmers have ever wondered where does good old realloc fit in C++. And that's a good question.
Could we improve [classref boost::container::vector vector] performance using memory expansion mechanisms
to avoid too many copies? But [classref boost::container::vector vector] is not the only container that
could benefit from an improved allocator interface: we could take advantage of the insertion of multiple
elements in [classref boost::container::list list] using a burst allocation mechanism that could amortize
costs (mutex locks, free memory searches...) that can't be amortized when using single node allocation
strategies.

These improvements require extending the STL allocator interface and use make use of a new
general purpose allocator since new and delete don't offer expansion and burst capabilities.

* [*Boost.Container] containers support an extended allocator interface based on an evolution of proposals
[@http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2006/n1953.html N1953: Upgrading the Interface of Allocators using API Versioning],
[@http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2006/n2045.html N2045: Improving STL allocators]
and the article
[@http://www.drivehq.com/web/igaztanaga/allocplus/ Applying classic memory allocation strategies to C++ containers].
The extended allocator interface is implemented by [classref boost::container::allocator allocator],
[classref boost::container::adaptive_pool adaptive_pool] and [classref boost::container::node_allocator node_allocator]
classes.

* Extended allocators use a modified [@http://g.oswego.edu/dl/html/malloc.html Doug Lea Malloc (DLMalloc)] low-level
allocator and offers an C API to implement memory expansion and burst allocations. DLmalloc is known to be very size
and speed efficient, and this allocator is used as the basis of many malloc implementations, including multithreaded
allocators built above DLmalloc (See [@http://www.malloc.de/en/ ptmalloc2, ptmalloc3] or
[@http://www.nedprod.com/programs/portable/nedmalloc/ nedmalloc]). This low-level allocator is implemented as
a separately compiled library whereas [classref boost::container::allocator allocator],
[classref boost::container::adaptive_pool adaptive_pool] and [classref boost::container::node_allocator node_allocator]
are header-only classes.

The following extended allocators are provided:

* [classref boost::container::allocator allocator]: This extended allocator offers expansion, shrink-in place
and burst allocation capabilities implemented as a thin wrapper around the modified DLMalloc.
It can be used with all containers and it should be the default choice when the programmer wants to use
extended allocator capabilities.

* [classref boost::container::node_allocator node_allocator]: It's a
[@http://www.boost.org/doc/libs/1_55_0/libs/pool/doc/html/boost_pool/pool/pooling.html#boost_pool.pool.pooling.simple Simple Segregated Storage]
allocator, similar to [*Boost.Pool] that takes advantage of the modified DLMalloc burst interface. It does not return
memory to the DLMalloc allocator (and thus, to the system), unless explicitly requested. It does offer a very small
memory overhead so it's suitable for node containers ([boost::container::list list], [boost::container::slist slist]
[boost::container::set set]...) that allocate very small `value_type`s and it offers improved node allocation times
for single node allocations with respecto to [classref boost::container::allocator allocator].

* [classref boost::container::adaptive_pool adaptive_pool]: It's a low-overhead node allocator that can return memory
to the system. The overhead can be very low (< 5% for small nodes) and it's nearly as fast as [classref boost::container::node_allocator node_allocator].
It's also suitable for node containers.

[endsect]

[/
/a__section:previous_element_slist Previous element for slist__a
/
/The C++11 `std::forward_list` class implement a singly linked list, similar to `slist`, and these
/containers only offer forward iterators and implement insertions and splice operations that operate with ranges
/to be inserted ['after] that position. In those cases, sometimes it's interesting to obtain an iterator pointing
/to the previous element of another element. This operation can be implemented
/
/a__endsect__a
]

[/
/a__section:get_stored_allocator Obtain stored allocator__a
/
Expand All @@ -532,18 +660,6 @@ using [@http://en.cppreference.com/w/cpp/language/default_initialization default
/http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2007/n2271.html
/
/a__endsect__a
/
/a__section:ordered_range_insertion Ordered range insertion (a__'ordered_unique_range__a, a__'ordered_range__a) __a
/
/a__endsect__a
/
/a__section:constant_time_range_splice Constant-time range splice__a
/
/a__endsect__a
/
/a__section:previous_element_slist Slist previous element__a
/
/a__endsect__a
/]

[endsect]
Expand Down Expand Up @@ -709,9 +825,10 @@ use [*Boost.Container]? There are several reasons for that:
* Default constructors don't allocate memory at all, which improves performance and
usually implies a no-throw guarantee (if predicate's or allocator's default constructor doesn't throw).
* Small string optimization for [classref boost::container::basic_string basic_string].
* New extensions beyond the standard based on user feedback to improve code performance.
* [link container.extended_functionality Extended functionality] beyond the standard based
on user feedback to improve code performance.
* You need a portable implementation that works when compiling without exceptions support or
you need to customize the error handling when a container needs to signall an exceptional error.
you need to customize the error handling when a container needs to signal an exceptional error.

[endsect]

Expand Down Expand Up @@ -759,6 +876,15 @@ use [*Boost.Container]? There are several reasons for that:

[section:release_notes Release Notes]

[section:release_notes_boost_1_56_00 Boost 1.56 Release]

* Added DlMalloc-based [link container.extended_functionality.extended_allocators Extended Allocators].

* Fixed bugs:
* [@https://svn.boost.org/trac/boost/ticket/9338 #9338: ['"VS2005 compiler errors in swap() definition after including container/memory_util.hpp"]].

[endsect]

[section:release_notes_boost_1_55_00 Boost 1.55 Release]

* Implemented [link container.main_features.scary_iterators SCARY iterators].
Expand All @@ -769,7 +895,8 @@ use [*Boost.Container]? There are several reasons for that:
[@https://svn.boost.org/trac/boost/ticket/9009 #9009],
[@https://svn.boost.org/trac/boost/ticket/9064 #9064],
[@https://svn.boost.org/trac/boost/ticket/9092 #9092],
[@https://svn.boost.org/trac/boost/ticket/9108 #9108].
[@https://svn.boost.org/trac/boost/ticket/9108 #9108],
[@https://svn.boost.org/trac/boost/ticket/9166 #9166],

[endsect]

Expand Down
2 changes: 1 addition & 1 deletion example/doc_emplace.cpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2009-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2009-2013. 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)
//
Expand Down
2 changes: 1 addition & 1 deletion example/doc_move_containers.cpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2009-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2009-2013. 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)
//
Expand Down
9 changes: 7 additions & 2 deletions example/doc_recursive_containers.cpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2009-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2009-2013. 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)
//
Expand All @@ -11,9 +11,10 @@
#include <boost/container/detail/workaround.hpp>
//[doc_recursive_containers
#include <boost/container/vector.hpp>
#include <boost/container/stable_vector.hpp>
#include <boost/container/deque.hpp>
#include <boost/container/list.hpp>
#include <boost/container/map.hpp>
#include <boost/container/stable_vector.hpp>
#include <boost/container/string.hpp>

using namespace boost::container;
Expand All @@ -23,6 +24,10 @@ struct data
int i_;
//A vector holding still undefined class 'data'
vector<data> v_;
//A stable_vector holding still undefined class 'data'
stable_vector<data> sv_;
//A stable_vector holding still undefined class 'data'
deque<data> d_;
//A list holding still undefined 'data'
list<data> l_;
//A map holding still undefined 'data'
Expand Down
2 changes: 1 addition & 1 deletion example/doc_type_erasure.cpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2009-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2009-2013. 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)
//
Expand Down
62 changes: 31 additions & 31 deletions include/boost/container/allocator_traits.hpp
Expand Up @@ -6,7 +6,7 @@
//
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2011-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2011-2013. 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)
//
Expand Down Expand Up @@ -38,7 +38,7 @@
#include <boost/container/detail/preprocessor.hpp>
#endif

///@cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

namespace boost {
namespace container {
Expand All @@ -56,7 +56,7 @@ struct is_std_allocator< std::allocator<T> >

} //namespace container_detail {

///@endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! The class template allocator_traits supplies a uniform interface to all allocator types.
//! This class is a C++03-compatible implementation of std::allocator_traits
Expand Down Expand Up @@ -94,29 +94,29 @@ struct allocator_traits
//!
typedef see_documentation size_type;
//! Alloc::propagate_on_container_copy_assignment if such a type exists, otherwise an integral_constant
//! type with internal constant static member `value` == false.
//! type with internal constant static member <code>value</code> == false.
typedef see_documentation 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 `value` == false.
//! type with internal constant static member <code>value</code> == false.
typedef see_documentation 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 `value` == false.
//! type with internal constant static member <code>value</code> == false.
typedef see_documentation 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 `rebind_alloc` is a struct derived from an allocator
//! In C++03 compilers <code>rebind_alloc</code> is a struct derived from an allocator
//! deduced by previously detailed rules.
template <class T> using rebind_alloc = see_documentation;

//! In C++03 compilers `rebind_traits` is a struct derived from
//! `allocator_traits<OtherAlloc>`, where `OtherAlloc` is
//! the allocator deduced by rules explained in `rebind_alloc`.
//! In C++03 compilers <code>rebind_traits</code> is a struct derived from
//! <code>allocator_traits<OtherAlloc></code>, where <code>OtherAlloc</code> is
//! the allocator deduced by rules explained in <code>rebind_alloc</code>.
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`.
//! <code>type</code> is an allocator related to Alloc deduced deduced by rules explained in <code>rebind_alloc</code>.
template <class T>
struct portable_rebind_alloc
{ typedef see_documentation type; };
Expand Down Expand Up @@ -206,19 +206,19 @@ struct allocator_traits
{ typedef typename boost::intrusive::detail::type_rebinder<Alloc, T>::type type; };
#endif //BOOST_CONTAINER_DOXYGEN_INVOKED

//! <b>Returns</b>: `a.allocate(n)`
//! <b>Returns</b>: <code>a.allocate(n)</code>
//!
static pointer allocate(Alloc &a, size_type n)
{ return a.allocate(n); }

//! <b>Returns</b>: `a.deallocate(p, n)`
//! <b>Returns</b>: <code>a.deallocate(p, n)</code>
//!
//! <b>Throws</b>: Nothing
static void deallocate(Alloc &a, pointer p, size_type n)
{ a.deallocate(p, n); }

//! <b>Effects</b>: calls `a.allocate(n, p)` if that call is well-formed;
//! otherwise, invokes `a.allocate(n)`
//! <b>Effects</b>: calls <code>a.allocate(n, p)</code> if that call is well-formed;
//! otherwise, invokes <code>a.allocate(n)</code>
static pointer allocate(Alloc &a, size_type n, const_void_pointer p)
{
const bool value = boost::container::container_detail::
Expand All @@ -228,10 +228,10 @@ struct allocator_traits
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()`.
//! <b>Effects</b>: calls <code>a.destroy(p)</code> if that call is well-formed;
//! otherwise, invokes <code>p->~T()</code>.
template<class T>
static void destroy(Alloc &a, T*p)
static void destroy(Alloc &a, T*p) BOOST_CONTAINER_NOEXCEPT
{
typedef T* destroy_pointer;
const bool value = boost::container::container_detail::
Expand All @@ -241,9 +241,9 @@ struct allocator_traits
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)
//! <b>Returns</b>: <code>a.max_size()</code> if that expression is well-formed; otherwise,
//! <code>numeric_limits<size_type>::max()</code>.
static size_type max_size(const Alloc &a) BOOST_CONTAINER_NOEXCEPT
{
const bool value = boost::container::container_detail::
has_member_function_callable_with_max_size
Expand All @@ -252,7 +252,7 @@ struct allocator_traits
return allocator_traits::priv_max_size(flag, a);
}

//! <b>Returns</b>: `a.select_on_container_copy_construction()` if that expression is well-formed;
//! <b>Returns</b>: <code>a.select_on_container_copy_construction()</code> if that expression is well-formed;
//! otherwise, a.
static
#if !defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
Expand All @@ -276,16 +276,16 @@ struct allocator_traits
}

#if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
//! <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)...)`
//! <b>Effects</b>: calls <code>a.construct(p, std::forward<Args>(args)...)</code> if that call is well-formed;
//! otherwise, invokes <code>::new (static_cast<void*>(p)) T(std::forward<Args>(args)...)</code>
template <class T, class ...Args>
static void construct(Alloc & a, T* p, BOOST_FWD_REF(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
///@cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
#if !defined(BOOST_CONTAINER_DOXYGEN_INVOKED)
private:
static pointer priv_allocate(boost::true_type, Alloc &a, size_type n, const_void_pointer p)
Expand All @@ -295,23 +295,23 @@ struct allocator_traits
{ return allocator_traits::allocate(a, n); }

template<class T>
static void priv_destroy(boost::true_type, Alloc &a, T* p)
static void priv_destroy(boost::true_type, Alloc &a, T* p) BOOST_CONTAINER_NOEXCEPT
{ a.destroy(p); }

template<class T>
static void priv_destroy(boost::false_type, Alloc &, T* p)
static void priv_destroy(boost::false_type, Alloc &, T* p) BOOST_CONTAINER_NOEXCEPT
{ p->~T(); (void)p; }

static size_type priv_max_size(boost::true_type, const Alloc &a)
static size_type priv_max_size(boost::true_type, const Alloc &a) BOOST_CONTAINER_NOEXCEPT
{ return a.max_size(); }

static size_type priv_max_size(boost::false_type, const Alloc &)
static size_type priv_max_size(boost::false_type, const Alloc &) BOOST_CONTAINER_NOEXCEPT
{ 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 const Alloc &priv_select_on_container_copy_construction(boost::false_type, const Alloc &a)
static const Alloc &priv_select_on_container_copy_construction(boost::false_type, const Alloc &a) BOOST_CONTAINER_NOEXCEPT
{ return a; }

#if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
Expand Down Expand Up @@ -394,7 +394,7 @@ struct allocator_traits
{ ::new((void*)p) T; }
#endif //#if defined(BOOST_CONTAINER_DOXYGEN_INVOKED)

///@endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

} //namespace container {
Expand Down
114 changes: 90 additions & 24 deletions include/boost/container/container_fwd.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -15,11 +15,35 @@
# pragma once
#endif

//! \file
//! This header file forward declares the following classes:
//! - boost::container::vector
//! - boost::container::stable_vector
//! - boost::container::static_vector
//! - boost::container::slist
//! - boost::container::list
//! - boost::container::set
//! - boost::container::multiset
//! - boost::container::map
//! - boost::container::multimap
//! - boost::container::flat_set
//! - boost::container::flat_multiset
//! - boost::container::flat_map
//! - boost::container::flat_multimap
//! - boost::container::basic_string
//! - boost::container::string
//! - boost::container::wstring
//! - boost::container::allocator
//! - boost::container::node_allocator
//! - boost::container::adaptive_pool
//!
//! and defines the following types:

//////////////////////////////////////////////////////////////////////////////
// Standard predeclarations
//////////////////////////////////////////////////////////////////////////////

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

namespace boost{
namespace intrusive{
Expand All @@ -32,13 +56,14 @@ namespace bi = boost::intrusive;

}}}

#include <cstddef>
#include <utility>
#include <memory>
#include <functional>
#include <iosfwd>
#include <string>

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//////////////////////////////////////////////////////////////////////////////
// Containers
Expand All @@ -47,89 +72,120 @@ namespace bi = boost::intrusive;
namespace boost {
namespace container {

//vector class
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

template <class T
,class Allocator = std::allocator<T> >
class vector;

//vector class
template <class T
,class Allocator = std::allocator<T> >
class stable_vector;

//vector class
template <class T, std::size_t Capacity>
class static_vector;

template <class T
,class Allocator = std::allocator<T> >
class deque;

//list class
template <class T
,class Allocator = std::allocator<T> >
class list;

//slist class
template <class T
,class Allocator = std::allocator<T> >
class slist;

//set class
template <class Key
,class Compare = std::less<Key>
,class Allocator = std::allocator<Key> >
class set;

//multiset class
template <class Key
,class Compare = std::less<Key>
,class Allocator = std::allocator<Key> >
class multiset;

//map class
template <class Key
,class T
,class Compare = std::less<Key>
,class Allocator = std::allocator<std::pair<const Key, T> > >
class map;

//multimap class
template <class Key
,class T
,class Compare = std::less<Key>
,class Allocator = std::allocator<std::pair<const Key, T> > >
class multimap;

//flat_set class
template <class Key
,class Compare = std::less<Key>
,class Allocator = std::allocator<Key> >
class flat_set;

//flat_multiset class
template <class Key
,class Compare = std::less<Key>
,class Allocator = std::allocator<Key> >
class flat_multiset;

//flat_map class
template <class Key
,class T
,class Compare = std::less<Key>
,class Allocator = std::allocator<std::pair<Key, T> > >
class flat_map;

//flat_multimap class
template <class Key
,class T
,class Compare = std::less<Key>
,class Allocator = std::allocator<std::pair<Key, T> > >
class flat_multimap;

//basic_string class
template <class CharT
,class Traits = std::char_traits<CharT>
,class Allocator = std::allocator<CharT> >
class basic_string;

typedef basic_string
<char
,std::char_traits<char>
,std::allocator<char> >
string;

typedef basic_string
<wchar_t
,std::char_traits<wchar_t>
,std::allocator<wchar_t> >
wstring;

static const std::size_t ADP_nodes_per_block = 256u;
static const std::size_t ADP_max_free_blocks = 2u;
static const std::size_t ADP_overhead_percent = 1u;
static const std::size_t ADP_only_alignment = 0u;

template < class T
, std::size_t NodesPerBlock = ADP_nodes_per_block
, std::size_t MaxFreeBlocks = ADP_max_free_blocks
, std::size_t OverheadPercent = ADP_overhead_percent
, unsigned Version = 2
>
class adaptive_pool;

template < class T
, unsigned Version = 2
, unsigned int AllocationDisableMask = 0>
class allocator;

static const std::size_t NodeAlloc_nodes_per_block = 256u;

template
< class T
, std::size_t NodesPerBlock = NodeAlloc_nodes_per_block
, std::size_t Version = 2>
class node_allocator;

#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! Type used to tag that the input range is
//! guaranteed to be ordered
struct ordered_range_t
Expand All @@ -149,17 +205,27 @@ struct ordered_unique_range_t
//! guaranteed to be ordered and unique
static const ordered_unique_range_t ordered_unique_range = ordered_unique_range_t();

//! Type used to tag that the input range is
//! guaranteed to be ordered and unique
//! Type used to tag that the inserted values
//! should be default initialized
struct default_init_t
{};

//! Value used to tag that the input range is
//! guaranteed to be ordered and unique
//! Value used to tag that the inserted values
//! should be default initialized
static const default_init_t default_init = default_init_t();
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! Type used to tag that the inserted values
//! should be value initialized
struct value_init_t
{};

//! Value used to tag that the inserted values
//! should be value initialized
static const value_init_t value_init = value_init_t();


namespace detail_really_deep_namespace {
namespace container_detail_really_deep_namespace {

//Otherwise, gcc issues a warning of previously defined
//anonymous_instance and unique_instance
Expand All @@ -175,7 +241,7 @@ struct dummy

} //detail_really_deep_namespace {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

}} //namespace boost { namespace container {

Expand Down
102 changes: 52 additions & 50 deletions include/boost/container/deque.hpp

Large diffs are not rendered by default.

7 changes: 4 additions & 3 deletions include/boost/container/detail/adaptive_node_pool_impl.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -15,9 +15,10 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/container_fwd.hpp>
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/container_fwd.hpp>
#include <boost/container/detail/utilities.hpp>
#include <boost/intrusive/pointer_traits.hpp>
#include <boost/intrusive/set.hpp>
Expand Down
370 changes: 368 additions & 2 deletions include/boost/container/detail/advanced_insert_int.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2008-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2008-2013. 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)
//
Expand All @@ -15,8 +15,373 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/allocator_traits.hpp>
#include <boost/container/detail/destroyers.hpp>
#include <boost/aligned_storage.hpp>
#include <boost/move/utility.hpp>
#include <iterator> //std::iterator_traits
#include <boost/assert.hpp>
#include <boost/detail/no_exceptions_support.hpp>

namespace boost { namespace container { namespace container_detail {

template<class A, class FwdIt, class Iterator>
struct move_insert_range_proxy
{
typedef typename allocator_traits<A>::size_type size_type;
typedef typename allocator_traits<A>::value_type value_type;

explicit move_insert_range_proxy(FwdIt first)
: first_(first)
{}

void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n)
{
this->first_ = ::boost::container::uninitialized_move_alloc_n_source
(a, this->first_, n, p);
}

void copy_n_and_update(A &, Iterator p, size_type n)
{
this->first_ = ::boost::container::move_n_source(this->first_, n, p);
}

FwdIt first_;
};


template<class A, class FwdIt, class Iterator>
struct insert_range_proxy
{
typedef typename allocator_traits<A>::size_type size_type;
typedef typename allocator_traits<A>::value_type value_type;

explicit insert_range_proxy(FwdIt first)
: first_(first)
{}

void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n)
{
this->first_ = ::boost::container::uninitialized_copy_alloc_n_source(a, this->first_, n, p);
}

void copy_n_and_update(A &, Iterator p, size_type n)
{
this->first_ = ::boost::container::copy_n_source(this->first_, n, p);
}

FwdIt first_;
};


template<class A, class Iterator>
struct insert_n_copies_proxy
{
typedef typename allocator_traits<A>::size_type size_type;
typedef typename allocator_traits<A>::value_type value_type;

explicit insert_n_copies_proxy(const value_type &v)
: v_(v)
{}

void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n) const
{ boost::container::uninitialized_fill_alloc_n(a, v_, n, p); }

void copy_n_and_update(A &, Iterator p, size_type n) const
{ std::fill_n(p, n, v_); }

const value_type &v_;
};

template<class A, class Iterator>
struct insert_value_initialized_n_proxy
{
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;

void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n) const
{ boost::container::uninitialized_value_init_alloc_n(a, n, p); }

void copy_n_and_update(A &, Iterator, size_type) const
{ BOOST_ASSERT(false); }
};

template<class A, class Iterator>
struct insert_default_initialized_n_proxy
{
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;

void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n) const
{ boost::container::uninitialized_default_init_alloc_n(a, n, p); }

void copy_n_and_update(A &, Iterator, size_type) const
{ BOOST_ASSERT(false); }
};

template<class A, class Iterator>
struct insert_copy_proxy
{
typedef boost::container::allocator_traits<A> alloc_traits;
typedef typename alloc_traits::size_type size_type;
typedef typename alloc_traits::value_type value_type;

explicit insert_copy_proxy(const value_type &v)
: v_(v)
{}

void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n) const
{
BOOST_ASSERT(n == 1); (void)n;
alloc_traits::construct( a, container_detail::to_raw_pointer(&*p), v_);
}

void copy_n_and_update(A &, Iterator p, size_type n) const
{
BOOST_ASSERT(n == 1); (void)n;
*p =v_;
}

const value_type &v_;
};


template<class A, class Iterator>
struct insert_move_proxy
{
typedef boost::container::allocator_traits<A> alloc_traits;
typedef typename alloc_traits::size_type size_type;
typedef typename alloc_traits::value_type value_type;

explicit insert_move_proxy(value_type &v)
: v_(v)
{}

void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n) const
{
BOOST_ASSERT(n == 1); (void)n;
alloc_traits::construct( a
, container_detail::to_raw_pointer(&*p)
, ::boost::move(v_)
);
}

void copy_n_and_update(A &, Iterator p, size_type n) const
{
BOOST_ASSERT(n == 1); (void)n;
*p = ::boost::move(v_);
}

value_type &v_;
};

template<class It, class A>
insert_move_proxy<A, It> get_insert_value_proxy(BOOST_RV_REF(typename std::iterator_traits<It>::value_type) v)
{
return insert_move_proxy<A, It>(v);
}

template<class It, class A>
insert_copy_proxy<A, It> get_insert_value_proxy(const typename std::iterator_traits<It>::value_type &v)
{
return insert_copy_proxy<A, It>(v);
}

}}} //namespace boost { namespace container { namespace container_detail {

#ifdef BOOST_CONTAINER_PERFECT_FORWARDING

#include <boost/container/detail/variadic_templates_tools.hpp>
#include <boost/move/utility.hpp>
#include <typeinfo>
//#include <iostream> //For debugging purposes

namespace boost {
namespace container {
namespace container_detail {

template<class A, class Iterator, class ...Args>
struct insert_non_movable_emplace_proxy
{
typedef boost::container::allocator_traits<A> alloc_traits;
typedef typename alloc_traits::size_type size_type;
typedef typename alloc_traits::value_type value_type;

typedef typename build_number_seq<sizeof...(Args)>::type index_tuple_t;

explicit insert_non_movable_emplace_proxy(Args&&... args)
: args_(args...)
{}

void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n)
{ this->priv_uninitialized_copy_some_and_update(a, index_tuple_t(), p, n); }

private:
template<int ...IdxPack>
void priv_uninitialized_copy_some_and_update(A &a, const index_tuple<IdxPack...>&, Iterator p, size_type n)
{
BOOST_ASSERT(n == 1); (void)n;
alloc_traits::construct( a
, container_detail::to_raw_pointer(&*p)
, ::boost::forward<Args>(get<IdxPack>(this->args_))...
);
}

protected:
tuple<Args&...> args_;
};

template<class A, class Iterator, class ...Args>
struct insert_emplace_proxy
: public insert_non_movable_emplace_proxy<A, Iterator, Args...>
{
typedef insert_non_movable_emplace_proxy<A, Iterator, Args...> base_t;
typedef boost::container::allocator_traits<A> alloc_traits;
typedef typename base_t::value_type value_type;
typedef typename base_t::size_type size_type;
typedef typename base_t::index_tuple_t index_tuple_t;

explicit insert_emplace_proxy(Args&&... args)
: base_t(::boost::forward<Args>(args)...)
{}

void copy_n_and_update(A &a, Iterator p, size_type n)
{ this->priv_copy_some_and_update(a, index_tuple_t(), p, n); }

private:

template<int ...IdxPack>
void priv_copy_some_and_update(A &a, const index_tuple<IdxPack...>&, Iterator p, size_type n)
{
BOOST_ASSERT(n ==1); (void)n;
aligned_storage<sizeof(value_type), alignment_of<value_type>::value> v;
value_type *vp = static_cast<value_type *>(static_cast<void *>(&v));
alloc_traits::construct(a, vp,
::boost::forward<Args>(get<IdxPack>(this->args_))...);
BOOST_TRY{
*p = ::boost::move(*vp);
}
BOOST_CATCH(...){
alloc_traits::destroy(a, vp);
BOOST_RETHROW
}
BOOST_CATCH_END
alloc_traits::destroy(a, vp);
}
};

}}} //namespace boost { namespace container { namespace container_detail {

#else //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING

#include <boost/container/detail/preprocessor.hpp>
#include <boost/container/detail/value_init.hpp>

namespace boost {
namespace container {
namespace container_detail {

#define BOOST_PP_LOCAL_MACRO(N) \
template<class A, class Iterator BOOST_PP_ENUM_TRAILING_PARAMS(N, class P) > \
struct BOOST_PP_CAT(insert_non_movable_emplace_proxy_arg, N) \
{ \
typedef boost::container::allocator_traits<A> alloc_traits; \
typedef typename alloc_traits::size_type size_type; \
typedef typename alloc_traits::value_type value_type; \
\
explicit BOOST_PP_CAT(insert_non_movable_emplace_proxy_arg, N) \
( BOOST_PP_ENUM(N, BOOST_CONTAINER_PP_PARAM_LIST, _) ) \
BOOST_PP_EXPR_IF(N, :) BOOST_PP_ENUM(N, BOOST_CONTAINER_PP_PARAM_INIT, _) \
{} \
\
void uninitialized_copy_n_and_update(A &a, Iterator p, size_type n) \
{ \
BOOST_ASSERT(n == 1); (void)n; \
alloc_traits::construct \
( a \
, container_detail::to_raw_pointer(&*p) \
BOOST_PP_ENUM_TRAILING(N, BOOST_CONTAINER_PP_MEMBER_FORWARD, _) \
); \
} \
\
void copy_n_and_update(A &, Iterator, size_type) \
{ BOOST_ASSERT(false); } \
\
protected: \
BOOST_PP_REPEAT(N, BOOST_CONTAINER_PP_PARAM_DEFINE, _) \
}; \
\
template<class A, class Iterator BOOST_PP_ENUM_TRAILING_PARAMS(N, class P) > \
struct BOOST_PP_CAT(insert_emplace_proxy_arg, N) \
: BOOST_PP_CAT(insert_non_movable_emplace_proxy_arg, N) \
< A, Iterator BOOST_PP_ENUM_TRAILING_PARAMS(N, P) > \
{ \
typedef BOOST_PP_CAT(insert_non_movable_emplace_proxy_arg, N) \
<A, Iterator BOOST_PP_ENUM_TRAILING_PARAMS(N, P) > base_t; \
typedef typename base_t::value_type value_type; \
typedef typename base_t::size_type size_type; \
typedef boost::container::allocator_traits<A> alloc_traits; \
\
explicit BOOST_PP_CAT(insert_emplace_proxy_arg, N) \
( BOOST_PP_ENUM(N, BOOST_CONTAINER_PP_PARAM_LIST, _) ) \
: base_t(BOOST_PP_ENUM(N, BOOST_CONTAINER_PP_PARAM_FORWARD, _) ) \
{} \
\
void copy_n_and_update(A &a, Iterator p, size_type n) \
{ \
BOOST_ASSERT(n == 1); (void)n; \
aligned_storage<sizeof(value_type), alignment_of<value_type>::value> v; \
value_type *vp = static_cast<value_type *>(static_cast<void *>(&v)); \
alloc_traits::construct(a, vp \
BOOST_PP_ENUM_TRAILING(N, BOOST_CONTAINER_PP_MEMBER_FORWARD, _)); \
BOOST_TRY{ \
*p = ::boost::move(*vp); \
} \
BOOST_CATCH(...){ \
alloc_traits::destroy(a, vp); \
BOOST_RETHROW \
} \
BOOST_CATCH_END \
alloc_traits::destroy(a, vp); \
} \
}; \
//!
#define BOOST_PP_LOCAL_LIMITS (0, BOOST_CONTAINER_MAX_CONSTRUCTOR_PARAMETERS)
#include BOOST_PP_LOCAL_ITERATE()

}}} //namespace boost { namespace container { namespace container_detail {

#endif //#ifdef BOOST_CONTAINER_PERFECT_FORWARDING

#include <boost/container/detail/config_end.hpp>

#endif //#ifndef BOOST_CONTAINER_ADVANCED_INSERT_INT_HPP
/*
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2008-2013. 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_ADVANCED_INSERT_INT_HPP
#define BOOST_CONTAINER_ADVANCED_INSERT_INT_HPP
#if defined(_MSC_VER)
# pragma once
#endif
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>
#include <boost/container/allocator_traits.hpp>
#include <boost/container/detail/destroyers.hpp>
#include <boost/aligned_storage.hpp>
Expand Down Expand Up @@ -391,3 +756,4 @@ struct BOOST_PP_CAT(insert_emplace_proxy_arg, N)
#include <boost/container/detail/config_end.hpp>
#endif //#ifndef BOOST_CONTAINER_ADVANCED_INSERT_INT_HPP
*/
4 changes: 2 additions & 2 deletions include/boost/container/detail/algorithms.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012.
// (C) Copyright Ion Gaztanaga 2005-2013.
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
Expand All @@ -17,7 +17,7 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/type_traits/has_trivial_copy.hpp>
Expand Down
8 changes: 4 additions & 4 deletions include/boost/container/detail/allocation_type.hpp
@@ -1,6 +1,6 @@
///////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -15,13 +15,13 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

namespace boost {
namespace container {

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
enum allocation_type_v
{
// constants for allocation commands
Expand All @@ -37,7 +37,7 @@ enum allocation_type_v
};

typedef int allocation_type;
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
static const allocation_type allocate_new = (allocation_type)allocate_new_v;
static const allocation_type expand_fwd = (allocation_type)expand_fwd_v;
static const allocation_type expand_bwd = (allocation_type)expand_bwd_v;
Expand Down
3 changes: 2 additions & 1 deletion include/boost/container/detail/allocator_version_traits.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2012-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2012-2013. 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)
//
Expand All @@ -17,6 +17,7 @@

#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/allocator_traits.hpp> //allocator_traits
#include <boost/container/throw_exception.hpp>
#include <boost/container/detail/multiallocation_chain.hpp> //multiallocation_chain
Expand Down
6 changes: 5 additions & 1 deletion include/boost/container/detail/config_begin.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -18,6 +18,10 @@
#define BOOST_CONTAINER_DETAIL_CRT_SECURE_NO_DEPRECATE
#define _CRT_SECURE_NO_DEPRECATE
#endif
#ifndef _SCL_SECURE_NO_WARNINGS
#define BOOST_CONTAINER_DETAIL_SCL_SECURE_NO_WARNINGS
#define _SCL_SECURE_NO_WARNINGS
#endif
#pragma warning (push)
#pragma warning (disable : 4702) // unreachable code
#pragma warning (disable : 4706) // assignment within conditional expression
Expand Down
6 changes: 5 additions & 1 deletion include/boost/container/detail/config_end.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -13,5 +13,9 @@
#undef BOOST_CONTAINER_DETAIL_CRT_SECURE_NO_DEPRECATE
#undef _CRT_SECURE_NO_DEPRECATE
#endif
#ifdef BOOST_CONTAINER_DETAIL_SCL_SECURE_NO_WARNINGS
#undef BOOST_CONTAINER_DETAIL_SCL_SECURE_NO_WARNINGS
#undef _SCL_SECURE_NO_WARNINGS
#endif
#endif

8 changes: 6 additions & 2 deletions include/boost/container/detail/destroyers.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012.
// (C) Copyright Ion Gaztanaga 2005-2013.
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
Expand All @@ -17,8 +17,9 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/detail/version_type.hpp>
#include <boost/container/detail/utilities.hpp>
#include <boost/container/allocator_traits.hpp>
Expand Down Expand Up @@ -231,6 +232,9 @@ struct null_scoped_destructor_n
void increment_size_backwards(size_type)
{}

void shrink_forward(size_type)
{}

void release()
{}
};
Expand Down
4 changes: 2 additions & 2 deletions include/boost/container/detail/flat_tree.hpp
@@ -1,6 +1,6 @@
////////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -15,7 +15,7 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/container_fwd.hpp>
Expand Down
2 changes: 1 addition & 1 deletion include/boost/container/detail/function_detector.hpp
@@ -1,6 +1,6 @@
/////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2009-2012.
// (C) Copyright Ion Gaztanaga 2009-2013.
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
Expand Down
4 changes: 2 additions & 2 deletions include/boost/container/detail/iterators.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012.
// (C) Copyright Ion Gaztanaga 2005-2013.
// (C) Copyright Gennaro Prota 2003 - 2004.
//
// Distributed under the Boost Software License, Version 1.0.
Expand All @@ -18,7 +18,7 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>
#include <boost/move/utility.hpp>
#include <boost/container/allocator_traits.hpp>
Expand Down
6 changes: 4 additions & 2 deletions include/boost/container/detail/math_functions.hpp
@@ -1,7 +1,7 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Stephen Cleary 2000.
// (C) Copyright Ion Gaztanaga 2007-2012.
// (C) Copyright Ion Gaztanaga 2007-2013.
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
Expand All @@ -16,7 +16,9 @@
#ifndef BOOST_CONTAINER_DETAIL_MATH_FUNCTIONS_HPP
#define BOOST_CONTAINER_DETAIL_MATH_FUNCTIONS_HPP

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <climits>
#include <boost/static_assert.hpp>

Expand Down
7 changes: 6 additions & 1 deletion include/boost/container/detail/mpl.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012.
// (C) Copyright Ion Gaztanaga 2005-2013.
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
Expand All @@ -17,6 +17,9 @@
# pragma once
#endif

#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <cstddef>

namespace boost {
Expand Down Expand Up @@ -156,5 +159,7 @@ template <> struct unvoid<const void> { struct type { }; };
} //namespace container {
} //namespace boost {

#include <boost/container/detail/config_end.hpp>

#endif //#ifndef BOOST_CONTAINER_CONTAINER_DETAIL_MPL_HPP

6 changes: 4 additions & 2 deletions include/boost/container/detail/multiallocation_chain.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -11,7 +11,9 @@
#ifndef BOOST_CONTAINER_DETAIL_MULTIALLOCATION_CHAIN_HPP
#define BOOST_CONTAINER_DETAIL_MULTIALLOCATION_CHAIN_HPP

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/container_fwd.hpp>
#include <boost/container/detail/utilities.hpp>
#include <boost/container/detail/type_traits.hpp>
Expand Down
4 changes: 2 additions & 2 deletions include/boost/container/detail/node_alloc_holder.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -15,7 +15,7 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <utility>
Expand Down
7 changes: 4 additions & 3 deletions include/boost/container/detail/node_pool_impl.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -15,9 +15,10 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/container_fwd.hpp>
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/container_fwd.hpp>
#include <boost/container/detail/utilities.hpp>
#include <boost/intrusive/pointer_traits.hpp>
#include <boost/intrusive/set.hpp>
Expand Down
4 changes: 2 additions & 2 deletions include/boost/container/detail/pair.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012.
// (C) Copyright Ion Gaztanaga 2005-2013.
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
Expand All @@ -17,7 +17,7 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/detail/mpl.hpp>
Expand Down
10 changes: 6 additions & 4 deletions include/boost/container/detail/pool_common.hpp
@@ -1,21 +1,23 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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_DETAIL_NODE_POOL_COMMON_HPP
#define BOOST_CONTAINER_DETAIL_NODE_POOL_COMMON_HPP
#ifndef BOOST_CONTAINER_DETAIL_POOL_COMMON_HPP
#define BOOST_CONTAINER_DETAIL_POOL_COMMON_HPP

#if defined(_MSC_VER)
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/intrusive/slist.hpp>
#include <new>

Expand Down
2 changes: 1 addition & 1 deletion include/boost/container/detail/preprocessor.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2008-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2008-2013. 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)
//
Expand Down
5 changes: 3 additions & 2 deletions include/boost/container/detail/transform_iterator.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012.
// (C) Copyright Ion Gaztanaga 2005-2013.
// (C) Copyright Gennaro Prota 2003 - 2004.
//
// Distributed under the Boost Software License, Version 1.0.
Expand All @@ -18,8 +18,9 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/detail/type_traits.hpp>
#include <iterator>

Expand Down
4 changes: 2 additions & 2 deletions include/boost/container/detail/tree.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -11,7 +11,7 @@
#ifndef BOOST_CONTAINER_TREE_HPP
#define BOOST_CONTAINER_TREE_HPP

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>
#include <boost/container/container_fwd.hpp>

Expand Down
5 changes: 3 additions & 2 deletions include/boost/container/detail/type_traits.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
// (C) Copyright John Maddock 2000.
// (C) Copyright Ion Gaztanaga 2005-2012.
// (C) Copyright Ion Gaztanaga 2005-2013.
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
Expand All @@ -19,7 +19,8 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/move/utility.hpp>

Expand Down
52 changes: 36 additions & 16 deletions include/boost/container/detail/utilities.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -11,8 +11,9 @@
#ifndef BOOST_CONTAINER_DETAIL_UTILITIES_HPP
#define BOOST_CONTAINER_DETAIL_UTILITIES_HPP

#include "config_begin.hpp"
#include "workaround.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <cstdio>
#include <cstring> //for ::memcpy
#include <boost/type_traits/is_fundamental.hpp>
Expand Down Expand Up @@ -110,18 +111,37 @@ template<class T>
const T &min_value(const T &a, const T &b)
{ return a < b ? a : b; }

template <class SizeType>
SizeType
get_next_capacity(const SizeType max_size
,const SizeType capacity
,const SizeType n)
enum NextCapacityOption { NextCapacityDouble, NextCapacity60Percent };

template<class SizeType, NextCapacityOption Option>
struct next_capacity_calculator;

template<class SizeType>
struct next_capacity_calculator<SizeType, NextCapacityDouble>
{
const SizeType remaining = max_size - capacity;
if ( remaining < n )
boost::container::throw_length_error("get_next_capacity, allocator's max_size reached");
const SizeType additional = max_value(n, capacity);
return ( remaining < additional ) ? max_size : ( capacity + additional );
#if 0 //Alternative for 50% grow
static SizeType get(const SizeType max_size
,const SizeType capacity
,const SizeType n)
{
const SizeType remaining = max_size - capacity;
if ( remaining < n )
boost::container::throw_length_error("get_next_capacity, allocator's max_size reached");
const SizeType additional = max_value(n, capacity);
return ( remaining < additional ) ? max_size : ( capacity + additional );
}
};


template<class SizeType>
struct next_capacity_calculator<SizeType, NextCapacity60Percent>
{
static SizeType get(const SizeType max_size
,const SizeType capacity
,const SizeType n)
{
const SizeType remaining = max_size - capacity;
if ( remaining < n )
boost::container::throw_length_error("get_next_capacity, allocator's max_size reached");
const SizeType m3 = max_size/3;

if (capacity < m3)
Expand All @@ -130,8 +150,8 @@ SizeType
if (capacity < m3*2)
return capacity + max_value((capacity+1)/2, n);
return max_size;
#endif
}
}
};

template <class T>
inline T* to_raw_pointer(T* p)
Expand Down
4 changes: 2 additions & 2 deletions include/boost/container/detail/value_init.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012.
// (C) Copyright Ion Gaztanaga 2005-2013.
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
Expand All @@ -17,7 +17,7 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

namespace boost {
Expand Down
5 changes: 3 additions & 2 deletions include/boost/container/detail/variadic_templates_tools.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2008-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2008-2013. 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)
//
Expand All @@ -15,8 +15,9 @@
# pragma once
#endif

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/detail/type_traits.hpp>
#include <cstddef> //std::size_t

Expand Down
7 changes: 4 additions & 3 deletions include/boost/container/detail/version_type.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand All @@ -16,7 +16,8 @@
#ifndef BOOST_CONTAINER_DETAIL_VERSION_TYPE_HPP
#define BOOST_CONTAINER_DETAIL_VERSION_TYPE_HPP

#include "config_begin.hpp"
#include <boost/container/detail/config_begin.hpp>
#include <boost/container/detail/workaround.hpp>

#include <boost/container/detail/mpl.hpp>
#include <boost/container/detail/type_traits.hpp>
Expand Down Expand Up @@ -87,6 +88,6 @@ struct version
} //namespace container {
} //namespace boost{

#include "config_end.hpp"
#include <boost/container/detail/config_end.hpp>

#endif //#define BOOST_CONTAINER_DETAIL_VERSION_TYPE_HPP
2 changes: 1 addition & 1 deletion include/boost/container/detail/workaround.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand Down
30 changes: 15 additions & 15 deletions include/boost/container/flat_map.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand Down Expand Up @@ -34,7 +34,7 @@
namespace boost {
namespace container {

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
// Forward declarations of operators == and <, needed for friend declarations.
template <class Key, class T, class Compare, class Allocator>
class flat_map;
Expand Down Expand Up @@ -63,7 +63,7 @@ static D force_copy(S s)
} //namespace container_detail{


/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! A flat_map is a kind of associative container that supports unique keys (contains at
//! most one of each key value) and provides for fast retrieval of values of another
Expand Down Expand Up @@ -95,7 +95,7 @@ template <class Key, class T, class Compare, class Allocator>
#endif
class flat_map
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(flat_map)
//This is the tree that we should store if pair was movable
Expand Down Expand Up @@ -129,7 +129,7 @@ class flat_map
<typename allocator_traits<Allocator>::pointer>::reverse_iterator reverse_iterator_impl;
typedef typename container_detail::get_flat_tree_iterators
<typename allocator_traits<Allocator>::pointer>::const_reverse_iterator const_reverse_iterator_impl;
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:

Expand Down Expand Up @@ -842,7 +842,7 @@ class flat_map
std::pair<const_iterator,const_iterator> equal_range(const key_type& x) const
{ return container_detail::force_copy<std::pair<const_iterator,const_iterator> >(m_flat_tree.equal_range(x)); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
template <class K1, class T1, class C1, class A1>
friend bool operator== (const flat_map<K1, T1, C1, A1>&,
const flat_map<K1, T1, C1, A1>&);
Expand Down Expand Up @@ -872,7 +872,7 @@ class flat_map
}
return (*i).second;
}
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class Key, class T, class Compare, class Allocator>
Expand Down Expand Up @@ -910,7 +910,7 @@ inline void swap(flat_map<Key,T,Compare,Allocator>& x,
flat_map<Key,T,Compare,Allocator>& y)
{ x.swap(y); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

} //namespace container {

Expand All @@ -935,7 +935,7 @@ inline bool operator==(const flat_multimap<Key,T,Compare,Allocator>& x,
template <class Key, class T, class Compare, class Allocator>
inline bool operator<(const flat_multimap<Key,T,Compare,Allocator>& x,
const flat_multimap<Key,T,Compare,Allocator>& y);
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! A flat_multimap is a kind of associative container that supports equivalent keys
//! (possibly containing multiple copies of the same key value) and provides for
Expand Down Expand Up @@ -967,7 +967,7 @@ template <class Key, class T, class Compare, class Allocator>
#endif
class flat_multimap
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(flat_multimap)
typedef container_detail::flat_tree<Key,
Expand Down Expand Up @@ -999,7 +999,7 @@ class flat_multimap
<typename allocator_traits<Allocator>::pointer>::reverse_iterator reverse_iterator_impl;
typedef typename container_detail::get_flat_tree_iterators
<typename allocator_traits<Allocator>::pointer>::const_reverse_iterator const_reverse_iterator_impl;
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:

Expand Down Expand Up @@ -1637,15 +1637,15 @@ class flat_multimap
std::pair<const_iterator,const_iterator> equal_range(const key_type& x) const
{ return container_detail::force_copy<std::pair<const_iterator,const_iterator> >(m_flat_tree.equal_range(x)); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
template <class K1, class T1, class C1, class A1>
friend bool operator== (const flat_multimap<K1, T1, C1, A1>& x,
const flat_multimap<K1, T1, C1, A1>& y);

template <class K1, class T1, class C1, class A1>
friend bool operator< (const flat_multimap<K1, T1, C1, A1>& x,
const flat_multimap<K1, T1, C1, A1>& y);
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class Key, class T, class Compare, class Allocator>
Expand Down Expand Up @@ -1684,7 +1684,7 @@ inline void swap(flat_multimap<Key,T,Compare,Allocator>& x, flat_multimap<Key,T,

}}

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

namespace boost {

Expand All @@ -1698,7 +1698,7 @@ struct has_trivial_destructor_after_move< boost::container::flat_multimap<K, T,

} //namespace boost {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

#include <boost/container/detail/config_end.hpp>

Expand Down
30 changes: 15 additions & 15 deletions include/boost/container/flat_set.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand Down Expand Up @@ -31,7 +31,7 @@
namespace boost {
namespace container {

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
// Forward declarations of operators < and ==, needed for friend declaration.

#ifdef BOOST_CONTAINER_DOXYGEN_INVOKED
Expand All @@ -48,7 +48,7 @@ inline bool operator==(const flat_set<Key,Compare,Allocator>& x,
template <class Key, class Compare, class Allocator>
inline bool operator<(const flat_set<Key,Compare,Allocator>& x,
const flat_set<Key,Compare,Allocator>& y);
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! flat_set is a Sorted Associative Container that stores objects of type Key.
//! It is also a Unique Associative Container, meaning that no two elements are the same.
Expand All @@ -68,12 +68,12 @@ template <class Key, class Compare, class Allocator>
#endif
class flat_set
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(flat_set)
typedef container_detail::flat_tree<Key, Key, container_detail::identity<Key>, Compare, Allocator> tree_t;
tree_t m_flat_tree; // flat tree representing flat_set
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//////////////////////////////////////////////
Expand Down Expand Up @@ -678,7 +678,7 @@ class flat_set
std::pair<iterator,iterator> equal_range(const key_type& x)
{ return m_flat_tree.equal_range(x); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
template <class K1, class C1, class A1>
friend bool operator== (const flat_set<K1,C1,A1>&, const flat_set<K1,C1,A1>&);

Expand All @@ -693,7 +693,7 @@ class flat_set
template<class KeyType>
iterator priv_insert(const_iterator p, BOOST_FWD_REF(KeyType) x)
{ return m_flat_tree.insert_unique(p, ::boost::forward<KeyType>(x)); }
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class Key, class Compare, class Allocator>
Expand Down Expand Up @@ -730,7 +730,7 @@ template <class Key, class Compare, class Allocator>
inline void swap(flat_set<Key,Compare,Allocator>& x, flat_set<Key,Compare,Allocator>& y)
{ x.swap(y); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

} //namespace container {

Expand Down Expand Up @@ -760,7 +760,7 @@ inline bool operator==(const flat_multiset<Key,Compare,Allocator>& x,
template <class Key, class Compare, class Allocator>
inline bool operator<(const flat_multiset<Key,Compare,Allocator>& x,
const flat_multiset<Key,Compare,Allocator>& y);
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! flat_multiset is a Sorted Associative Container that stores objects of type Key.
//!
Expand All @@ -781,12 +781,12 @@ template <class Key, class Compare, class Allocator>
#endif
class flat_multiset
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(flat_multiset)
typedef container_detail::flat_tree<Key, Key, container_detail::identity<Key>, Compare, Allocator> tree_t;
tree_t m_flat_tree; // flat tree representing flat_multiset
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//////////////////////////////////////////////
Expand Down Expand Up @@ -1353,7 +1353,7 @@ class flat_multiset
std::pair<iterator,iterator> equal_range(const key_type& x)
{ return m_flat_tree.equal_range(x); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
template <class K1, class C1, class A1>
friend bool operator== (const flat_multiset<K1,C1,A1>&,
const flat_multiset<K1,C1,A1>&);
Expand All @@ -1368,7 +1368,7 @@ class flat_multiset
template <class KeyType>
iterator priv_insert(const_iterator p, BOOST_FWD_REF(KeyType) x)
{ return m_flat_tree.insert_equal(p, ::boost::forward<KeyType>(x)); }
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class Key, class Compare, class Allocator>
Expand Down Expand Up @@ -1405,7 +1405,7 @@ template <class Key, class Compare, class Allocator>
inline void swap(flat_multiset<Key,Compare,Allocator>& x, flat_multiset<Key,Compare,Allocator>& y)
{ x.swap(y); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

} //namespace container {

Expand All @@ -1419,7 +1419,7 @@ struct has_trivial_destructor_after_move<boost::container::flat_multiset<Key, C,

namespace container {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

}}

Expand Down
18 changes: 9 additions & 9 deletions include/boost/container/list.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand Down Expand Up @@ -47,7 +47,7 @@
namespace boost {
namespace container {

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
namespace container_detail {

template<class VoidPointer>
Expand Down Expand Up @@ -99,7 +99,7 @@ struct intrusive_list_type
};

} //namespace container_detail {
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! A list is a doubly linked list. That is, it is a Sequence that supports both
//! forward and backward traversal, and (amortized) constant time insertion and
Expand All @@ -120,7 +120,7 @@ class list
: protected container_detail::node_alloc_holder
<Allocator, typename container_detail::intrusive_list_type<Allocator>::type>
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
typedef typename
container_detail::intrusive_list_type<Allocator>::type Icont;
typedef container_detail::node_alloc_holder<Allocator, Icont> AllocHolder;
Expand Down Expand Up @@ -167,7 +167,7 @@ class list

typedef container_detail::iterator<typename Icont::iterator, false> iterator_impl;
typedef container_detail::iterator<typename Icont::iterator, true> const_iterator_impl;
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//////////////////////////////////////////////
Expand Down Expand Up @@ -1216,7 +1216,7 @@ class list
void reverse() BOOST_CONTAINER_NOEXCEPT
{ this->icont().reverse(); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:

bool priv_try_shrink(size_type new_size)
Expand Down Expand Up @@ -1303,7 +1303,7 @@ class list
bool operator()(const value_type &a, const value_type &b) const
{ return a == b; }
};
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

};

Expand Down Expand Up @@ -1362,7 +1362,7 @@ inline void swap(list<T, Allocator>& x, list<T, Allocator>& y)
x.swap(y);
}

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

} //namespace container {

Expand All @@ -1375,7 +1375,7 @@ struct has_trivial_destructor_after_move<boost::container::list<T, Allocator> >

namespace container {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

}}

Expand Down
30 changes: 15 additions & 15 deletions include/boost/container/map.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand Down Expand Up @@ -39,7 +39,7 @@
namespace boost {
namespace container {

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
// Forward declarations of operators == and <, needed for friend declarations.
template <class Key, class T, class Compare, class Allocator>
inline bool operator==(const map<Key,T,Compare,Allocator>& x,
Expand All @@ -48,7 +48,7 @@ inline bool operator==(const map<Key,T,Compare,Allocator>& x,
template <class Key, class T, class Compare, class Allocator>
inline bool operator<(const map<Key,T,Compare,Allocator>& x,
const map<Key,T,Compare,Allocator>& y);
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! A map is a kind of associative container that supports unique keys (contains at
//! most one of each key value) and provides for fast retrieval of values of another
Expand All @@ -69,7 +69,7 @@ template <class Key, class T, class Compare, class Allocator>
#endif
class map
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(map)

Expand All @@ -81,7 +81,7 @@ class map
< Key, value_type_impl, Compare, container_detail::select1st<value_type_impl>
> value_compare_impl;
tree_t m_tree; // red-black tree representing map
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//////////////////////////////////////////////
Expand Down Expand Up @@ -755,7 +755,7 @@ class map
std::pair<const_iterator,const_iterator> equal_range(const key_type& x) const
{ return m_tree.equal_range(x); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
template <class K1, class T1, class C1, class A1>
friend bool operator== (const map<K1, T1, C1, A1>&,
const map<K1, T1, C1, A1>&);
Expand Down Expand Up @@ -790,7 +790,7 @@ class map
return (*i).second;
}

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class Key, class T, class Compare, class Allocator>
Expand Down Expand Up @@ -827,7 +827,7 @@ template <class Key, class T, class Compare, class Allocator>
inline void swap(map<Key,T,Compare,Allocator>& x, map<Key,T,Compare,Allocator>& y)
{ x.swap(y); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

// Forward declaration of operators < and ==, needed for friend declaration.

Expand All @@ -851,7 +851,7 @@ struct has_trivial_destructor_after_move<boost::container::map<K, T, C, Allocato

namespace container {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! A multimap is a kind of associative container that supports equivalent keys
//! (possibly containing multiple copies of the same key value) and provides for
Expand All @@ -873,7 +873,7 @@ template <class Key, class T, class Compare, class Allocator>
#endif
class multimap
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(multimap)

Expand All @@ -885,7 +885,7 @@ class multimap
< Key, value_type_impl, Compare, container_detail::select1st<value_type_impl>
> value_compare_impl;
tree_t m_tree; // red-black tree representing map
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//////////////////////////////////////////////
Expand Down Expand Up @@ -1463,15 +1463,15 @@ class multimap
std::pair<const_iterator,const_iterator> equal_range(const key_type& x) const
{ return m_tree.equal_range(x); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
template <class K1, class T1, class C1, class A1>
friend bool operator== (const multimap<K1, T1, C1, A1>& x,
const multimap<K1, T1, C1, A1>& y);

template <class K1, class T1, class C1, class A1>
friend bool operator< (const multimap<K1, T1, C1, A1>& x,
const multimap<K1, T1, C1, A1>& y);
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class Key, class T, class Compare, class Allocator>
Expand Down Expand Up @@ -1508,7 +1508,7 @@ template <class Key, class T, class Compare, class Allocator>
inline void swap(multimap<Key,T,Compare,Allocator>& x, multimap<Key,T,Compare,Allocator>& y)
{ x.swap(y); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

} //namespace container {

Expand All @@ -1522,7 +1522,7 @@ struct has_trivial_destructor_after_move<boost::container::multimap<K, T, C, All

namespace container {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

}}

Expand Down
132 changes: 66 additions & 66 deletions include/boost/container/scoped_allocator.hpp

Large diffs are not rendered by default.

10 changes: 7 additions & 3 deletions include/boost/container/scoped_allocator_fwd.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2011-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2011-2013. 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)
//
Expand All @@ -11,6 +11,10 @@
#ifndef BOOST_CONTAINER_ALLOCATOR_SCOPED_ALLOCATOR_FWD_HPP
#define BOOST_CONTAINER_ALLOCATOR_SCOPED_ALLOCATOR_FWD_HPP

//! \file
//! This header file forward declares boost::container::scoped_allocator_adaptor
//! and defines the following types:

#if defined(_MSC_VER)
# pragma once
#endif
Expand All @@ -25,7 +29,7 @@

namespace boost { namespace container {

///@cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

#if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)

Expand Down Expand Up @@ -55,7 +59,7 @@ class scoped_allocator_adaptor;

#endif

///@endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! The allocator_arg_t struct is an empty structure type used as a unique type to
//! disambiguate constructor and function overloading. Specifically, several types
Expand Down
30 changes: 15 additions & 15 deletions include/boost/container/set.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2005-2013. 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)
//
Expand Down Expand Up @@ -35,7 +35,7 @@
namespace boost {
namespace container {

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
// Forward declarations of operators < and ==, needed for friend declaration.
template <class Key, class Compare, class Allocator>
inline bool operator==(const set<Key,Compare,Allocator>& x,
Expand All @@ -44,7 +44,7 @@ inline bool operator==(const set<Key,Compare,Allocator>& x,
template <class Key, class Compare, class Allocator>
inline bool operator<(const set<Key,Compare,Allocator>& x,
const set<Key,Compare,Allocator>& y);
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! A set is a kind of associative container that supports unique keys (contains at
//! most one of each key value) and provides for fast retrieval of the keys themselves.
Expand All @@ -60,13 +60,13 @@ template <class Key, class Compare, class Allocator>
#endif
class set
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(set)
typedef container_detail::rbtree<Key, Key,
container_detail::identity<Key>, Compare, Allocator> tree_t;
tree_t m_tree; // red-black tree representing set
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//////////////////////////////////////////////
Expand Down Expand Up @@ -600,7 +600,7 @@ class set
std::pair<const_iterator, const_iterator> equal_range(const key_type& x) const
{ return m_tree.equal_range(x); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
template <class K1, class C1, class A1>
friend bool operator== (const set<K1,C1,A1>&, const set<K1,C1,A1>&);

Expand All @@ -615,7 +615,7 @@ class set
template <class KeyType>
iterator priv_insert(const_iterator p, BOOST_FWD_REF(KeyType) x)
{ return m_tree.insert_unique(p, ::boost::forward<KeyType>(x)); }
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class Key, class Compare, class Allocator>
Expand Down Expand Up @@ -652,7 +652,7 @@ template <class Key, class Compare, class Allocator>
inline void swap(set<Key,Compare,Allocator>& x, set<Key,Compare,Allocator>& y)
{ x.swap(y); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

} //namespace container {

Expand All @@ -675,7 +675,7 @@ inline bool operator==(const multiset<Key,Compare,Allocator>& x,
template <class Key, class Compare, class Allocator>
inline bool operator<(const multiset<Key,Compare,Allocator>& x,
const multiset<Key,Compare,Allocator>& y);
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! A multiset is a kind of associative container that supports equivalent keys
//! (possibly contains multiple copies of the same key value) and provides for
Expand All @@ -691,13 +691,13 @@ template <class Key, class Compare, class Allocator>
#endif
class multiset
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(multiset)
typedef container_detail::rbtree<Key, Key,
container_detail::identity<Key>, Compare, Allocator> tree_t;
tree_t m_tree; // red-black tree representing multiset
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:

Expand Down Expand Up @@ -1221,7 +1221,7 @@ class multiset
std::pair<const_iterator, const_iterator> equal_range(const key_type& x) const
{ return m_tree.equal_range(x); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
template <class K1, class C1, class A1>
friend bool operator== (const multiset<K1,C1,A1>&,
const multiset<K1,C1,A1>&);
Expand All @@ -1237,7 +1237,7 @@ class multiset
iterator priv_insert(const_iterator p, BOOST_FWD_REF(KeyType) x)
{ return m_tree.insert_equal(p, ::boost::forward<KeyType>(x)); }

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class Key, class Compare, class Allocator>
Expand Down Expand Up @@ -1274,7 +1274,7 @@ template <class Key, class Compare, class Allocator>
inline void swap(multiset<Key,Compare,Allocator>& x, multiset<Key,Compare,Allocator>& y)
{ x.swap(y); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

} //namespace container {

Expand All @@ -1288,7 +1288,7 @@ struct has_trivial_destructor_after_move<boost::container::multiset<Key, C, Allo

namespace container {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

}}

Expand Down
22 changes: 11 additions & 11 deletions include/boost/container/slist.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2004-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2004-2013. 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)
//
Expand Down Expand Up @@ -48,7 +48,7 @@
namespace boost {
namespace container {

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

template <class T, class Allocator>
class slist;
Expand Down Expand Up @@ -106,7 +106,7 @@ struct intrusive_slist_type

} //namespace container_detail {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! An slist is a singly linked list: a list where each element is linked to the next
//! element, but not to the previous element. That is, it is a Sequence that
Expand Down Expand Up @@ -149,7 +149,7 @@ class slist
: protected container_detail::node_alloc_holder
<Allocator, typename container_detail::intrusive_slist_type<Allocator>::type>
{
/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
typedef typename
container_detail::intrusive_slist_type<Allocator>::type Icont;
typedef container_detail::node_alloc_holder<Allocator, Icont> AllocHolder;
Expand Down Expand Up @@ -195,7 +195,7 @@ class slist
BOOST_COPYABLE_AND_MOVABLE(slist)
typedef container_detail::iterator<typename Icont::iterator, false> iterator_impl;
typedef container_detail::iterator<typename Icont::iterator, true > const_iterator_impl;
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//////////////////////////////////////////////
Expand Down Expand Up @@ -1423,7 +1423,7 @@ class slist
void splice(const_iterator p, BOOST_RV_REF(slist) x, const_iterator first, const_iterator last) BOOST_CONTAINER_NOEXCEPT
{ this->splice(p, static_cast<slist&>(x), first, last); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:

void priv_push_front (const T &x)
Expand Down Expand Up @@ -1505,7 +1505,7 @@ class slist

const value_type &m_ref;
};
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <class T, class Allocator>
Expand Down Expand Up @@ -1561,7 +1561,7 @@ inline void swap(slist<T,Allocator>& x, slist<T,Allocator>& y)

}}

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

namespace boost {

Expand All @@ -1574,14 +1574,14 @@ struct has_trivial_destructor_after_move<boost::container::slist<T, Allocator> >

namespace container {

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

}} //namespace boost{ namespace container {

// Specialization of insert_iterator so that insertions will be constant
// time rather than linear time.

///@cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//Ummm, I don't like to define things in namespace std, but
//there is no other way
Expand Down Expand Up @@ -1620,7 +1620,7 @@ class insert_iterator<boost::container::slist<T, Allocator> >

} //namespace std;

///@endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

#include <boost/container/detail/config_end.hpp>

Expand Down
26 changes: 13 additions & 13 deletions include/boost/container/stable_vector.hpp
@@ -1,6 +1,6 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2008-2012. Distributed under the Boost
// (C) Copyright Ion Gaztanaga 2008-2013. 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)
//
Expand Down Expand Up @@ -47,18 +47,18 @@
#include <memory>
#include <new> //placement new

///@cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

#include <boost/container/vector.hpp>

//#define STABLE_VECTOR_ENABLE_INVARIANT_CHECKING

///@endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

namespace boost {
namespace container {

///@cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

namespace stable_vector_detail{

Expand Down Expand Up @@ -393,7 +393,7 @@ struct index_traits

#endif //#if !defined(BOOST_CONTAINER_DOXYGEN_INVOKED)

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//! Originally developed by Joaquin M. Lopez Munoz, stable_vector is a std::vector
//! drop-in replacement implemented as a node container, offering iterator and reference
Expand Down Expand Up @@ -433,7 +433,7 @@ template <class T, class Allocator>
#endif
class stable_vector
{
///@cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
typedef allocator_traits<Allocator> allocator_traits_type;
typedef boost::intrusive::
pointer_traits
Expand Down Expand Up @@ -504,7 +504,7 @@ class stable_vector
typedef stable_vector_detail::iterator
< typename allocator_traits<Allocator>::pointer
, false> const_iterator_impl;
///@endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
public:

//////////////////////////////////////////////
Expand All @@ -526,7 +526,7 @@ class stable_vector
typedef BOOST_CONTAINER_IMPDEF(std::reverse_iterator<iterator>) reverse_iterator;
typedef BOOST_CONTAINER_IMPDEF(std::reverse_iterator<const_iterator>) const_reverse_iterator;

///@cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
private:
BOOST_COPYABLE_AND_MOVABLE(stable_vector)
static const size_type ExtraPointers = index_traits_type::ExtraPointers;
Expand All @@ -536,7 +536,7 @@ class stable_vector

class push_back_rollback;
friend class push_back_rollback;
///@endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//////////////////////////////////////////////
Expand Down Expand Up @@ -1510,7 +1510,7 @@ class stable_vector
void clear() BOOST_CONTAINER_NOEXCEPT
{ this->erase(this->cbegin(),this->cend()); }

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

private:

Expand Down Expand Up @@ -1836,7 +1836,7 @@ class stable_vector
const node_allocator_type &priv_node_alloc() const { return internal_data; }

index_type index;
/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
};

template <typename T,typename Allocator>
Expand Down Expand Up @@ -1883,11 +1883,11 @@ void swap(stable_vector<T,Allocator>& x,stable_vector<T,Allocator>& y)
x.swap(y);
}

/// @cond
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

#undef STABLE_VECTOR_CHECK_INVARIANT

/// @endcond
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

/*
Expand Down
64 changes: 33 additions & 31 deletions include/boost/container/static_vector.hpp
Expand Up @@ -21,6 +21,8 @@

namespace boost { namespace container {

#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

namespace container_detail {

template<class T, std::size_t N>
Expand Down Expand Up @@ -61,46 +63,46 @@ class static_storage_allocator

} //namespace container_detail {

/**
* @defgroup static_vector_non_member static_vector non-member functions
*/

/**
* @brief A variable-size array container with fixed capacity.
*
* static_vector is a sequence container like boost::container::vector with contiguous storage that can
* change in size, along with the static allocation, low overhead, and fixed capacity of boost::array.
*
* A static_vector is a sequence that supports random access to elements, constant time insertion and
* removal of elements at the end, and linear time insertion and removal of elements at the beginning or
* in the middle. The number of elements in a static_vector may vary dynamically up to a fixed capacity
* because elements are stored within the object itself similarly to an array. However, objects are
* initialized as they are inserted into static_vector unlike C arrays or std::array which must construct
* all elements on instantiation. The behavior of static_vector enables the use of statically allocated
* elements in cases with complex object lifetime requirements that would otherwise not be trivially
* possible.
*
* @par Error Handling
* Insertion beyond the capacity result in throwing std::bad_alloc() if exceptions are enabled or
* calling throw_bad_alloc() if not enabled.
*
* std::out_of_range is thrown if out of bound access is performed in `at()` if exceptions are
* enabled, throw_out_of_range() if not enabled.
*
* @tparam Value The type of element that will be stored.
* @tparam Capacity The maximum number of elements static_vector can store, fixed at compile time.
*/
#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

//!
//!@brief A variable-size array container with fixed capacity.
//!
//!static_vector is a sequence container like boost::container::vector with contiguous storage that can
//!change in size, along with the static allocation, low overhead, and fixed capacity of boost::array.
//!
//!A static_vector is a sequence that supports random access to elements, constant time insertion and
//!removal of elements at the end, and linear time insertion and removal of elements at the beginning or
//!in the middle. The number of elements in a static_vector may vary dynamically up to a fixed capacity
//!because elements are stored within the object itself similarly to an array. However, objects are
//!initialized as they are inserted into static_vector unlike C arrays or std::array which must construct
//!all elements on instantiation. The behavior of static_vector enables the use of statically allocated
//!elements in cases with complex object lifetime requirements that would otherwise not be trivially
//!possible.
//!
//!@par Error Handling
//! Insertion beyond the capacity result in throwing std::bad_alloc() if exceptions are enabled or
//! calling throw_bad_alloc() if not enabled.
//!
//! std::out_of_range is thrown if out of bound access is performed in <code>at()</code> if exceptions are
//! enabled, throw_out_of_range() if not enabled.
//!
//!@tparam Value The type of element that will be stored.
//!@tparam Capacity The maximum number of elements static_vector can store, fixed at compile time.
template <typename Value, std::size_t Capacity>
class static_vector
: public vector<Value, container_detail::static_storage_allocator<Value, Capacity> >
{
typedef vector<Value, container_detail::static_storage_allocator<Value, Capacity> > base_t;
#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED
typedef vector<Value, container_detail::static_storage_allocator<Value, Capacity> > base_t;

BOOST_COPYABLE_AND_MOVABLE(static_vector)
BOOST_COPYABLE_AND_MOVABLE(static_vector)

template<class U, std::size_t OtherCapacity>
friend class static_vector;

#endif //#ifndef BOOST_CONTAINER_DOXYGEN_INVOKED

public:
//! @brief The type of elements stored in the container.
typedef typename base_t::value_type value_type;
Expand Down