mirror of
https://github.com/boostorg/unordered.git
synced 2025-07-31 20:04:29 +02:00
Unordered: Starting to support allocator_traits.
[SVN r73678]
This commit is contained in:
@@ -1,9 +1,12 @@
|
|||||||
|
|
||||||
// Copyright 2005-2011 Daniel James.
|
// Copyright 2005-2011 Daniel James.
|
||||||
|
// Copyright 2009 Pablo Halpern.
|
||||||
|
//
|
||||||
// Distributed under the Boost Software License, Version 1.0. (See accompanying
|
// 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)
|
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
//
|
||||||
// A couple of templates to make using allocators easier.
|
// Written by Daniel James using some code from Pablo Halpern's
|
||||||
|
// allocator traits implementation.
|
||||||
|
|
||||||
#ifndef BOOST_UNORDERED_DETAIL_ALLOCATOR_UTILITIES_HPP_INCLUDED
|
#ifndef BOOST_UNORDERED_DETAIL_ALLOCATOR_UTILITIES_HPP_INCLUDED
|
||||||
#define BOOST_UNORDERED_DETAIL_ALLOCATOR_UTILITIES_HPP_INCLUDED
|
#define BOOST_UNORDERED_DETAIL_ALLOCATOR_UTILITIES_HPP_INCLUDED
|
||||||
@@ -13,6 +16,7 @@
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include <boost/config.hpp>
|
#include <boost/config.hpp>
|
||||||
|
#include <boost/detail/select_type.hpp>
|
||||||
|
|
||||||
#if (defined(BOOST_NO_STD_ALLOCATOR) || defined(BOOST_DINKUMWARE_STDLIB)) \
|
#if (defined(BOOST_NO_STD_ALLOCATOR) || defined(BOOST_DINKUMWARE_STDLIB)) \
|
||||||
&& !defined(__BORLANDC__)
|
&& !defined(__BORLANDC__)
|
||||||
@@ -23,24 +27,185 @@
|
|||||||
# include <boost/detail/allocator_utilities.hpp>
|
# include <boost/detail/allocator_utilities.hpp>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if BOOST_UNORDERED_USE_ALLOCATOR_TRAITS
|
||||||
|
# include <memory>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if !defined(BOOST_NO_0X_HDR_TYPE_TRAITS)
|
||||||
|
#include <type_traits>
|
||||||
|
namespace boost { namespace unordered { namespace detail {
|
||||||
|
using std::integral_constant;
|
||||||
|
using std::true_type;
|
||||||
|
using std::false_type;
|
||||||
|
}}}
|
||||||
|
#else
|
||||||
|
namespace boost { namespace unordered { namespace detail {
|
||||||
|
template <typename T, T Value>
|
||||||
|
struct integral_constant { enum { value = Value }; };
|
||||||
|
typedef integral_constant<bool, true> true_type;
|
||||||
|
typedef integral_constant<bool, false> false_type;
|
||||||
|
}}}
|
||||||
|
#endif
|
||||||
|
|
||||||
namespace boost { namespace unordered { namespace detail {
|
namespace boost { namespace unordered { namespace detail {
|
||||||
|
|
||||||
|
#if BOOST_UNORDERED_USE_ALLOCATOR_TRAITS
|
||||||
|
template <typename Alloc>
|
||||||
|
struct allocator_traits : std::allocator_traits<Alloc> {};
|
||||||
|
|
||||||
|
template <typename Alloc, typename T>
|
||||||
|
struct rebind_wrap
|
||||||
|
{
|
||||||
|
typedef typename allocator_traits<Alloc>::rebind_alloc<T> type;
|
||||||
|
};
|
||||||
|
#else
|
||||||
// rebind_wrap
|
// rebind_wrap
|
||||||
//
|
//
|
||||||
// Rebind allocators. For some problematic libraries, use rebind_to
|
// Rebind allocators. For some problematic libraries, use rebind_to
|
||||||
// from <boost/detail/allocator_utilities.hpp>.
|
// from <boost/detail/allocator_utilities.hpp>.
|
||||||
|
|
||||||
#if defined(BOOST_UNORDERED_USE_ALLOCATOR_UTILITIES)
|
# if defined(BOOST_UNORDERED_USE_ALLOCATOR_UTILITIES)
|
||||||
template <class Alloc, class T>
|
template <typename Alloc, typename T>
|
||||||
struct rebind_wrap : ::boost::detail::allocator::rebind_to<Alloc, T> {};
|
struct rebind_wrap : ::boost::detail::allocator::rebind_to<Alloc, T> {};
|
||||||
#else
|
# else
|
||||||
template <class Alloc, class T>
|
template <typename Alloc, typename T>
|
||||||
struct rebind_wrap
|
struct rebind_wrap
|
||||||
{
|
{
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
Alloc::BOOST_NESTED_TEMPLATE rebind<T>::other
|
Alloc::BOOST_NESTED_TEMPLATE rebind<T>::other
|
||||||
type;
|
type;
|
||||||
};
|
};
|
||||||
|
# endif
|
||||||
|
|
||||||
|
struct convertible_from_anything
|
||||||
|
{
|
||||||
|
template<typename T> convertible_from_anything(T const&);
|
||||||
|
};
|
||||||
|
|
||||||
|
// Infrastructure for providing a default type for Tp::tname if absent.
|
||||||
|
#define BOOST_DEFAULT_TYPE_TMPLT(tname) \
|
||||||
|
template <typename Tp, typename Default> \
|
||||||
|
struct default_type_ ## tname { \
|
||||||
|
\
|
||||||
|
template <typename X> \
|
||||||
|
static char test(int, BOOST_DEDUCED_TYPENAME X::tname*); \
|
||||||
|
\
|
||||||
|
template <typename X> \
|
||||||
|
static int test(convertible_from_anything, void*); \
|
||||||
|
\
|
||||||
|
struct DefaultWrap { typedef Default tname; }; \
|
||||||
|
\
|
||||||
|
static const bool value = (1 == sizeof(test<Tp>(0, 0))); \
|
||||||
|
\
|
||||||
|
typedef BOOST_DEDUCED_TYPENAME \
|
||||||
|
boost::detail::if_true<value>:: \
|
||||||
|
BOOST_NESTED_TEMPLATE then<Tp, DefaultWrap> \
|
||||||
|
::type::tname type; \
|
||||||
|
}
|
||||||
|
|
||||||
|
#define BOOST_DEFAULT_TYPE(T,tname, arg) \
|
||||||
|
BOOST_DEDUCED_TYPENAME default_type_ ## tname<T, arg>::type
|
||||||
|
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(pointer);
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(const_pointer);
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(void_pointer);
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(const_void_pointer);
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(difference_type);
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(size_type);
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(propagate_on_container_copy_assignment);
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(propagate_on_container_move_assignment);
|
||||||
|
BOOST_DEFAULT_TYPE_TMPLT(propagate_on_container_swap);
|
||||||
|
|
||||||
|
template <typename Alloc>
|
||||||
|
struct allocator_traits
|
||||||
|
{
|
||||||
|
typedef Alloc allocator_type;
|
||||||
|
typedef typename Alloc::value_type value_type;
|
||||||
|
|
||||||
|
typedef BOOST_DEFAULT_TYPE(Alloc, pointer, value_type*)
|
||||||
|
pointer;
|
||||||
|
|
||||||
|
// For now always use the allocator's const_pointer.
|
||||||
|
|
||||||
|
//typedef BOOST_DEFAULT_TYPE(Alloc, const_pointer,
|
||||||
|
// BOOST_DEDUCED_TYPENAME pointer_traits<pointer>::
|
||||||
|
// BOOST_NESTED_TEMPLATE rebind<const value_type>::other)
|
||||||
|
// const_pointer;
|
||||||
|
|
||||||
|
typedef BOOST_DEFAULT_TYPE(Alloc, const_pointer, value_type const*)
|
||||||
|
const_pointer;
|
||||||
|
|
||||||
|
// I'm not using void pointers for now.
|
||||||
|
|
||||||
|
//typedef BOOST_DEFAULT_TYPE(Alloc, void_pointer,
|
||||||
|
// BOOST_NESTED_TEMPLATE pointer_traits<pointer>::
|
||||||
|
// BOOST_NESTED_TEMPLATE rebind<void>::other)
|
||||||
|
// void_pointer;
|
||||||
|
|
||||||
|
//typedef BOOST_DEFAULT_TYPE(Alloc, const_void_pointer,
|
||||||
|
// BOOST_DEDUCED_TYPENAME pointer_traits<pointer>::
|
||||||
|
// BOOST_NESTED_TEMPLATE rebind<const void>::other)
|
||||||
|
// const_void_pointer;
|
||||||
|
|
||||||
|
typedef BOOST_DEFAULT_TYPE(Alloc, difference_type, std::ptrdiff_t)
|
||||||
|
difference_type;
|
||||||
|
|
||||||
|
typedef BOOST_DEFAULT_TYPE(Alloc, size_type, std::size_t)
|
||||||
|
size_type;
|
||||||
|
|
||||||
|
// TODO: rebind_alloc and rebind_traits
|
||||||
|
|
||||||
|
static pointer allocate(Alloc& a, size_type n)
|
||||||
|
{ return a.allocate(n); }
|
||||||
|
|
||||||
|
// I never use this, so I'll just comment it out for now.
|
||||||
|
//
|
||||||
|
//static pointer allocate(Alloc& a, size_type n, const_void_pointer hint)
|
||||||
|
// { return DEFAULT_FUNC(allocate, pointer)(a, n, hint); }
|
||||||
|
|
||||||
|
static void deallocate(Alloc& a, pointer p, size_type n)
|
||||||
|
{ a.deallocate(p, n); }
|
||||||
|
|
||||||
|
// Only support the basic copy constructor
|
||||||
|
|
||||||
|
// template <typename T, typename... Args>
|
||||||
|
// static void construct(Alloc& a, T* p, Args&&... args) {
|
||||||
|
// DEFAULT_FUNC(construct,void)(a, p, std::forward<Args>(args)...);
|
||||||
|
// }
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
static void construct(Alloc& a, T* p, T const& x) {
|
||||||
|
a.construct(p, x);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
static void destroy(Alloc& a, T* p) {
|
||||||
|
// DEFAULT_FUNC(destroy,void)(a, p);
|
||||||
|
a.destroy(p);
|
||||||
|
}
|
||||||
|
|
||||||
|
static size_type max_size(const Alloc& a)
|
||||||
|
{ return a.max_size(); }
|
||||||
|
|
||||||
|
// Allocator propagation on construction
|
||||||
|
|
||||||
|
static Alloc select_on_container_copy_construction(const Alloc& rhs) {
|
||||||
|
//return BOOST_DEFAULT_FUNC(select_on_container_copy_construction,Alloc)(rhs);
|
||||||
|
return rhs;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Allocator propagation on assignment and swap.
|
||||||
|
// Return true if lhs is modified.
|
||||||
|
typedef BOOST_DEFAULT_TYPE(
|
||||||
|
Alloc, propagate_on_container_copy_assignment, false_type)
|
||||||
|
propagate_on_container_copy_assignment;
|
||||||
|
typedef BOOST_DEFAULT_TYPE(
|
||||||
|
Alloc,propagate_on_container_move_assignment, false_type)
|
||||||
|
propagate_on_container_move_assignment;
|
||||||
|
typedef BOOST_DEFAULT_TYPE(
|
||||||
|
Alloc,propagate_on_container_swap,false_type)
|
||||||
|
propagate_on_container_swap;
|
||||||
|
};
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// allocator_array_constructor
|
// allocator_array_constructor
|
||||||
@@ -49,10 +214,11 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
// clean up if an exception is thrown before the container takes charge
|
// clean up if an exception is thrown before the container takes charge
|
||||||
// of it.
|
// of it.
|
||||||
|
|
||||||
template <class Allocator>
|
template <typename Allocator>
|
||||||
struct allocator_array_constructor
|
struct allocator_array_constructor
|
||||||
{
|
{
|
||||||
typedef BOOST_DEDUCED_TYPENAME Allocator::pointer pointer;
|
typedef BOOST_DEDUCED_TYPENAME allocator_traits<Allocator>::pointer
|
||||||
|
pointer;
|
||||||
|
|
||||||
Allocator& alloc_;
|
Allocator& alloc_;
|
||||||
pointer ptr_;
|
pointer ptr_;
|
||||||
@@ -69,21 +235,21 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
~allocator_array_constructor() {
|
~allocator_array_constructor() {
|
||||||
if (ptr_) {
|
if (ptr_) {
|
||||||
for(pointer p = ptr_; p != constructed_; ++p)
|
for(pointer p = ptr_; p != constructed_; ++p)
|
||||||
alloc_.destroy(p);
|
allocator_traits<Allocator>::destroy(alloc_, p);
|
||||||
|
|
||||||
alloc_.deallocate(ptr_, length_);
|
allocator_traits<Allocator>::deallocate(alloc_, ptr_, length_);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class V>
|
template <typename V>
|
||||||
void construct(V const& v, std::size_t l)
|
void construct(V const& v, std::size_t l)
|
||||||
{
|
{
|
||||||
BOOST_ASSERT(!ptr_);
|
BOOST_ASSERT(!ptr_);
|
||||||
length_ = l;
|
length_ = l;
|
||||||
ptr_ = alloc_.allocate(length_);
|
ptr_ = allocator_traits<Allocator>::allocate(alloc_, length_);
|
||||||
pointer end = ptr_ + static_cast<std::ptrdiff_t>(length_);
|
pointer end = ptr_ + static_cast<std::ptrdiff_t>(length_);
|
||||||
for(constructed_ = ptr_; constructed_ != end; ++constructed_)
|
for(constructed_ = ptr_; constructed_ != end; ++constructed_)
|
||||||
alloc_.construct(constructed_, v);
|
allocator_traits<Allocator>::construct(alloc_, constructed_, v);
|
||||||
}
|
}
|
||||||
|
|
||||||
pointer get() const
|
pointer get() const
|
||||||
|
@@ -49,16 +49,16 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
|
|
||||||
typedef A value_allocator;
|
typedef A value_allocator;
|
||||||
typedef ::boost::unordered::detail::bucket<A> bucket;
|
typedef ::boost::unordered::detail::bucket<A> bucket;
|
||||||
typedef BOOST_DEDUCED_TYPENAME A::value_type value_type;
|
typedef BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type value_type;
|
||||||
|
|
||||||
typedef BOOST_DEDUCED_TYPENAME bucket::bucket_allocator
|
typedef BOOST_DEDUCED_TYPENAME bucket::bucket_allocator
|
||||||
bucket_allocator;
|
bucket_allocator;
|
||||||
typedef BOOST_DEDUCED_TYPENAME bucket::bucket_ptr bucket_ptr;
|
typedef BOOST_DEDUCED_TYPENAME allocator_traits<bucket_allocator>::pointer bucket_ptr;
|
||||||
typedef BOOST_DEDUCED_TYPENAME bucket::node_ptr node_ptr;
|
typedef BOOST_DEDUCED_TYPENAME bucket::node_ptr node_ptr;
|
||||||
|
|
||||||
typedef BOOST_DEDUCED_TYPENAME rebind_wrap<value_allocator, node>::type
|
typedef BOOST_DEDUCED_TYPENAME rebind_wrap<value_allocator, node>::type
|
||||||
node_allocator;
|
node_allocator;
|
||||||
typedef BOOST_DEDUCED_TYPENAME node_allocator::pointer real_node_ptr;
|
typedef BOOST_DEDUCED_TYPENAME allocator_traits<node_allocator>::pointer real_node_ptr;
|
||||||
|
|
||||||
// Members
|
// Members
|
||||||
|
|
||||||
@@ -91,7 +91,7 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
std::size_t max_bucket_count() const
|
std::size_t max_bucket_count() const
|
||||||
{
|
{
|
||||||
// -1 to account for the start bucket.
|
// -1 to account for the start bucket.
|
||||||
return prev_prime(this->bucket_alloc().max_size() - 1);
|
return prev_prime(allocator_traits<bucket_allocator>::max_size(bucket_alloc()) - 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////
|
||||||
@@ -184,8 +184,8 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
real_node_ptr real_ptr(node_alloc().address(*raw_ptr));
|
real_node_ptr real_ptr(node_alloc().address(*raw_ptr));
|
||||||
|
|
||||||
::boost::unordered::detail::destroy(raw_ptr->value_ptr());
|
::boost::unordered::detail::destroy(raw_ptr->value_ptr());
|
||||||
node_alloc().destroy(real_ptr);
|
allocator_traits<node_allocator>::destroy(node_alloc(), real_ptr);
|
||||||
node_alloc().deallocate(real_ptr, 1);
|
allocator_traits<node_allocator>::deallocate(node_alloc(), real_ptr, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
void delete_buckets()
|
void delete_buckets()
|
||||||
@@ -202,10 +202,10 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
|
|
||||||
++end;
|
++end;
|
||||||
for(bucket_ptr begin = this->buckets_; begin != end; ++begin) {
|
for(bucket_ptr begin = this->buckets_; begin != end; ++begin) {
|
||||||
bucket_alloc().destroy(begin);
|
allocator_traits<bucket_allocator>::destroy(bucket_alloc(), begin);
|
||||||
}
|
}
|
||||||
|
|
||||||
bucket_alloc().deallocate(this->buckets_, this->bucket_count_ + 1);
|
allocator_traits<bucket_allocator>::deallocate(bucket_alloc(), this->buckets_, this->bucket_count_ + 1);
|
||||||
|
|
||||||
this->buckets_ = bucket_ptr();
|
this->buckets_ = bucket_ptr();
|
||||||
}
|
}
|
||||||
@@ -476,6 +476,7 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
typedef BOOST_DEDUCED_TYPENAME buckets::node node;
|
typedef BOOST_DEDUCED_TYPENAME buckets::node node;
|
||||||
typedef BOOST_DEDUCED_TYPENAME buckets::real_node_ptr real_node_ptr;
|
typedef BOOST_DEDUCED_TYPENAME buckets::real_node_ptr real_node_ptr;
|
||||||
typedef BOOST_DEDUCED_TYPENAME buckets::value_type value_type;
|
typedef BOOST_DEDUCED_TYPENAME buckets::value_type value_type;
|
||||||
|
typedef BOOST_DEDUCED_TYPENAME buckets::node_allocator node_allocator;
|
||||||
|
|
||||||
buckets& buckets_;
|
buckets& buckets_;
|
||||||
real_node_ptr node_;
|
real_node_ptr node_;
|
||||||
@@ -570,9 +571,9 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (node_constructed_)
|
if (node_constructed_)
|
||||||
buckets_.node_alloc().destroy(node_);
|
allocator_traits<node_allocator>::destroy(buckets_.node_alloc(), node_);
|
||||||
|
|
||||||
buckets_.node_alloc().deallocate(node_, 1);
|
allocator_traits<node_allocator>::deallocate(buckets_.node_alloc(), node_, 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -583,8 +584,8 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
node_constructed_ = false;
|
node_constructed_ = false;
|
||||||
value_constructed_ = false;
|
value_constructed_ = false;
|
||||||
|
|
||||||
node_ = buckets_.node_alloc().allocate(1);
|
node_ = allocator_traits<node_allocator>::allocate(buckets_.node_alloc(), 1);
|
||||||
buckets_.node_alloc().construct(node_, node());
|
allocator_traits<node_allocator>::construct(buckets_.node_alloc(), node_, node());
|
||||||
node_->init(buckets_.bucket_alloc().address(*node_));
|
node_->init(buckets_.bucket_alloc().address(*node_));
|
||||||
|
|
||||||
node_constructed_ = true;
|
node_constructed_ = true;
|
||||||
|
@@ -279,10 +279,10 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
|
|
||||||
template <class H, class P, class A>
|
template <class H, class P, class A>
|
||||||
struct multiset : public types<
|
struct multiset : public types<
|
||||||
BOOST_DEDUCED_TYPENAME A::value_type,
|
BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type,
|
||||||
BOOST_DEDUCED_TYPENAME A::value_type,
|
BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type,
|
||||||
H, P, A,
|
H, P, A,
|
||||||
set_extractor<BOOST_DEDUCED_TYPENAME A::value_type>,
|
set_extractor<BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type>,
|
||||||
false>
|
false>
|
||||||
{
|
{
|
||||||
typedef equivalent_table<multiset<H, P, A> > impl;
|
typedef equivalent_table<multiset<H, P, A> > impl;
|
||||||
@@ -291,9 +291,9 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
|
|
||||||
template <class K, class H, class P, class A>
|
template <class K, class H, class P, class A>
|
||||||
struct multimap : public types<
|
struct multimap : public types<
|
||||||
K, BOOST_DEDUCED_TYPENAME A::value_type,
|
K, BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type,
|
||||||
H, P, A,
|
H, P, A,
|
||||||
map_extractor<K, BOOST_DEDUCED_TYPENAME A::value_type>,
|
map_extractor<K, BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type>,
|
||||||
false>
|
false>
|
||||||
{
|
{
|
||||||
typedef equivalent_table<multimap<K, H, P, A> > impl;
|
typedef equivalent_table<multimap<K, H, P, A> > impl;
|
||||||
|
@@ -28,7 +28,7 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
//
|
//
|
||||||
// For unordered_set/unordered_map:
|
// For unordered_set/unordered_map:
|
||||||
//
|
//
|
||||||
// bucket<A> value_base<A::value_type>
|
// bucket<A> value_base<allocator_traits<A>::value_type>
|
||||||
// | |
|
// | |
|
||||||
// +--------------+-------------+
|
// +--------------+-------------+
|
||||||
// |
|
// |
|
||||||
@@ -36,7 +36,7 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
//
|
//
|
||||||
// For unordered_multiset/unordered_multimap:
|
// For unordered_multiset/unordered_multimap:
|
||||||
//
|
//
|
||||||
// bucket<A> value_base<A::value_type>
|
// bucket<A> value_base<allocator_traits<A>::value_type>
|
||||||
// | |
|
// | |
|
||||||
// +--------------+-------------+
|
// +--------------+-------------+
|
||||||
// |
|
// |
|
||||||
@@ -57,7 +57,8 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
::boost::unordered::detail::rebind_wrap<A, bucket>::type
|
::boost::unordered::detail::rebind_wrap<A, bucket>::type
|
||||||
bucket_allocator;
|
bucket_allocator;
|
||||||
typedef BOOST_DEDUCED_TYPENAME bucket_allocator::pointer bucket_ptr;
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
|
allocator_traits<bucket_allocator>::pointer bucket_ptr;
|
||||||
typedef bucket_ptr node_ptr;
|
typedef bucket_ptr node_ptr;
|
||||||
|
|
||||||
node_ptr next_;
|
node_ptr next_;
|
||||||
@@ -101,12 +102,12 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
template <class A>
|
template <class A>
|
||||||
struct ungrouped_node
|
struct ungrouped_node
|
||||||
: ::boost::unordered::detail::bucket<A>,
|
: ::boost::unordered::detail::bucket<A>,
|
||||||
value_base<BOOST_DEDUCED_TYPENAME A::value_type>
|
value_base<BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type>
|
||||||
{
|
{
|
||||||
typedef ::boost::unordered::detail::bucket<A> bucket;
|
typedef ::boost::unordered::detail::bucket<A> bucket;
|
||||||
typedef BOOST_DEDUCED_TYPENAME bucket::bucket_ptr bucket_ptr;
|
typedef BOOST_DEDUCED_TYPENAME bucket::bucket_ptr bucket_ptr;
|
||||||
typedef BOOST_DEDUCED_TYPENAME bucket::node_ptr node_ptr;
|
typedef BOOST_DEDUCED_TYPENAME bucket::node_ptr node_ptr;
|
||||||
typedef BOOST_DEDUCED_TYPENAME A::value_type value_type;
|
typedef BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type value_type;
|
||||||
|
|
||||||
std::size_t hash_;
|
std::size_t hash_;
|
||||||
|
|
||||||
@@ -176,12 +177,12 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
template <class A>
|
template <class A>
|
||||||
struct grouped_node
|
struct grouped_node
|
||||||
: ::boost::unordered::detail::bucket<A>,
|
: ::boost::unordered::detail::bucket<A>,
|
||||||
value_base<BOOST_DEDUCED_TYPENAME A::value_type>
|
value_base<BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type>
|
||||||
{
|
{
|
||||||
typedef ::boost::unordered::detail::bucket<A> bucket;
|
typedef ::boost::unordered::detail::bucket<A> bucket;
|
||||||
typedef BOOST_DEDUCED_TYPENAME bucket::bucket_ptr bucket_ptr;
|
typedef BOOST_DEDUCED_TYPENAME bucket::bucket_ptr bucket_ptr;
|
||||||
typedef BOOST_DEDUCED_TYPENAME bucket::node_ptr node_ptr;
|
typedef BOOST_DEDUCED_TYPENAME bucket::node_ptr node_ptr;
|
||||||
typedef BOOST_DEDUCED_TYPENAME A::value_type value_type;
|
typedef BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type value_type;
|
||||||
|
|
||||||
std::size_t hash_;
|
std::size_t hash_;
|
||||||
node_ptr group_prev_;
|
node_ptr group_prev_;
|
||||||
|
@@ -617,13 +617,13 @@ namespace boost { namespace unordered { namespace iterator_detail {
|
|||||||
class l_iterator
|
class l_iterator
|
||||||
: public ::boost::iterator <
|
: public ::boost::iterator <
|
||||||
std::forward_iterator_tag,
|
std::forward_iterator_tag,
|
||||||
BOOST_DEDUCED_TYPENAME A::value_type,
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type,
|
||||||
std::ptrdiff_t,
|
std::ptrdiff_t,
|
||||||
BOOST_DEDUCED_TYPENAME A::pointer,
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::pointer,
|
||||||
BOOST_DEDUCED_TYPENAME A::reference>
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type&>
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef BOOST_DEDUCED_TYPENAME A::value_type value_type;
|
typedef BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type value_type;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef ::boost::unordered::detail::buckets<A, Unique> buckets;
|
typedef ::boost::unordered::detail::buckets<A, Unique> buckets;
|
||||||
@@ -641,7 +641,7 @@ namespace boost { namespace unordered { namespace iterator_detail {
|
|||||||
l_iterator() : ptr_() {}
|
l_iterator() : ptr_() {}
|
||||||
l_iterator(node_ptr x, std::size_t b, std::size_t c)
|
l_iterator(node_ptr x, std::size_t b, std::size_t c)
|
||||||
: ptr_(x), bucket_(b), bucket_count_(c) {}
|
: ptr_(x), bucket_(b), bucket_count_(c) {}
|
||||||
BOOST_DEDUCED_TYPENAME A::reference operator*() const {
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type& operator*() const {
|
||||||
return node::get_value(ptr_);
|
return node::get_value(ptr_);
|
||||||
}
|
}
|
||||||
value_type* operator->() const {
|
value_type* operator->() const {
|
||||||
@@ -678,13 +678,13 @@ namespace boost { namespace unordered { namespace iterator_detail {
|
|||||||
class cl_iterator
|
class cl_iterator
|
||||||
: public ::boost::iterator <
|
: public ::boost::iterator <
|
||||||
std::forward_iterator_tag,
|
std::forward_iterator_tag,
|
||||||
BOOST_DEDUCED_TYPENAME A::value_type,
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type,
|
||||||
std::ptrdiff_t,
|
std::ptrdiff_t,
|
||||||
BOOST_DEDUCED_TYPENAME A::const_pointer,
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::const_pointer,
|
||||||
BOOST_DEDUCED_TYPENAME A::const_reference >
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type const& >
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef BOOST_DEDUCED_TYPENAME A::value_type value_type;
|
typedef BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type value_type;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef ::boost::unordered::detail::buckets<A, Unique> buckets;
|
typedef ::boost::unordered::detail::buckets<A, Unique> buckets;
|
||||||
@@ -705,7 +705,7 @@ namespace boost { namespace unordered { namespace iterator_detail {
|
|||||||
cl_iterator(local_iterator x)
|
cl_iterator(local_iterator x)
|
||||||
: ptr_(x.ptr_), bucket_(x.bucket_), bucket_count_(x.bucket_count_)
|
: ptr_(x.ptr_), bucket_(x.bucket_), bucket_count_(x.bucket_count_)
|
||||||
{}
|
{}
|
||||||
BOOST_DEDUCED_TYPENAME A::const_reference
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type const&
|
||||||
operator*() const {
|
operator*() const {
|
||||||
return node::get_value(ptr_);
|
return node::get_value(ptr_);
|
||||||
}
|
}
|
||||||
@@ -743,13 +743,13 @@ namespace boost { namespace unordered { namespace iterator_detail {
|
|||||||
class iterator
|
class iterator
|
||||||
: public ::boost::iterator <
|
: public ::boost::iterator <
|
||||||
std::forward_iterator_tag,
|
std::forward_iterator_tag,
|
||||||
BOOST_DEDUCED_TYPENAME A::value_type,
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type,
|
||||||
std::ptrdiff_t,
|
std::ptrdiff_t,
|
||||||
BOOST_DEDUCED_TYPENAME A::pointer,
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::pointer,
|
||||||
BOOST_DEDUCED_TYPENAME A::reference >
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type& >
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef BOOST_DEDUCED_TYPENAME A::value_type value_type;
|
typedef BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type value_type;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef ::boost::unordered::detail::buckets<A, Unique> buckets;
|
typedef ::boost::unordered::detail::buckets<A, Unique> buckets;
|
||||||
@@ -763,7 +763,7 @@ namespace boost { namespace unordered { namespace iterator_detail {
|
|||||||
|
|
||||||
iterator() : node_() {}
|
iterator() : node_() {}
|
||||||
explicit iterator(node_ptr const& x) : node_(x) {}
|
explicit iterator(node_ptr const& x) : node_(x) {}
|
||||||
BOOST_DEDUCED_TYPENAME A::reference operator*() const {
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type& operator*() const {
|
||||||
return node::get_value(node_);
|
return node::get_value(node_);
|
||||||
}
|
}
|
||||||
value_type* operator->() const {
|
value_type* operator->() const {
|
||||||
@@ -793,13 +793,13 @@ namespace boost { namespace unordered { namespace iterator_detail {
|
|||||||
class c_iterator
|
class c_iterator
|
||||||
: public ::boost::iterator <
|
: public ::boost::iterator <
|
||||||
std::forward_iterator_tag,
|
std::forward_iterator_tag,
|
||||||
BOOST_DEDUCED_TYPENAME A::value_type,
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type,
|
||||||
std::ptrdiff_t,
|
std::ptrdiff_t,
|
||||||
BOOST_DEDUCED_TYPENAME A::const_pointer,
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::const_pointer,
|
||||||
BOOST_DEDUCED_TYPENAME A::const_reference >
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type const& >
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef BOOST_DEDUCED_TYPENAME A::value_type value_type;
|
typedef BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type value_type;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef ::boost::unordered::detail::buckets<A, Unique> buckets;
|
typedef ::boost::unordered::detail::buckets<A, Unique> buckets;
|
||||||
@@ -829,7 +829,7 @@ namespace boost { namespace unordered { namespace iterator_detail {
|
|||||||
c_iterator() : node_() {}
|
c_iterator() : node_() {}
|
||||||
explicit c_iterator(node_ptr const& x) : node_(x) {}
|
explicit c_iterator(node_ptr const& x) : node_(x) {}
|
||||||
c_iterator(iterator const& x) : node_(x.node_) {}
|
c_iterator(iterator const& x) : node_(x.node_) {}
|
||||||
BOOST_DEDUCED_TYPENAME A::const_reference operator*() const {
|
BOOST_DEDUCED_TYPENAME boost::unordered::detail::allocator_traits<A>::value_type const& operator*() const {
|
||||||
return node::get_value(node_);
|
return node::get_value(node_);
|
||||||
}
|
}
|
||||||
value_type const* operator->() const {
|
value_type const* operator->() const {
|
||||||
|
@@ -370,10 +370,10 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
|
|
||||||
template <class H, class P, class A>
|
template <class H, class P, class A>
|
||||||
struct set : public types<
|
struct set : public types<
|
||||||
BOOST_DEDUCED_TYPENAME A::value_type,
|
BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type,
|
||||||
BOOST_DEDUCED_TYPENAME A::value_type,
|
BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type,
|
||||||
H, P, A,
|
H, P, A,
|
||||||
set_extractor<BOOST_DEDUCED_TYPENAME A::value_type>,
|
set_extractor<BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type>,
|
||||||
true>
|
true>
|
||||||
{
|
{
|
||||||
typedef ::boost::unordered::detail::unique_table<set<H, P, A> > impl;
|
typedef ::boost::unordered::detail::unique_table<set<H, P, A> > impl;
|
||||||
@@ -382,9 +382,9 @@ namespace boost { namespace unordered { namespace detail {
|
|||||||
|
|
||||||
template <class K, class H, class P, class A>
|
template <class K, class H, class P, class A>
|
||||||
struct map : public types<
|
struct map : public types<
|
||||||
K, BOOST_DEDUCED_TYPENAME A::value_type,
|
K, BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type,
|
||||||
H, P, A,
|
H, P, A,
|
||||||
map_extractor<K, BOOST_DEDUCED_TYPENAME A::value_type>,
|
map_extractor<K, BOOST_DEDUCED_TYPENAME allocator_traits<A>::value_type>,
|
||||||
true>
|
true>
|
||||||
{
|
{
|
||||||
typedef ::boost::unordered::detail::unique_table<map<K, H, P, A> > impl;
|
typedef ::boost::unordered::detail::unique_table<map<K, H, P, A> > impl;
|
||||||
|
@@ -56,6 +56,7 @@ namespace unordered
|
|||||||
::boost::unordered::detail::rebind_wrap<
|
::boost::unordered::detail::rebind_wrap<
|
||||||
allocator_type, value_type>::type
|
allocator_type, value_type>::type
|
||||||
value_allocator;
|
value_allocator;
|
||||||
|
typedef ::boost::unordered::detail::allocator_traits<value_allocator> allocator_traits;
|
||||||
|
|
||||||
typedef ::boost::unordered::detail::map<K, H, P,
|
typedef ::boost::unordered::detail::map<K, H, P,
|
||||||
value_allocator> types;
|
value_allocator> types;
|
||||||
@@ -66,13 +67,12 @@ namespace unordered
|
|||||||
public:
|
public:
|
||||||
|
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
value_allocator::pointer pointer;
|
allocator_traits::pointer pointer;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
value_allocator::const_pointer const_pointer;
|
allocator_traits::const_pointer const_pointer;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
|
||||||
value_allocator::reference reference;
|
typedef value_type& reference;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef value_type const& const_reference;
|
||||||
value_allocator::const_reference const_reference;
|
|
||||||
|
|
||||||
typedef std::size_t size_type;
|
typedef std::size_t size_type;
|
||||||
typedef std::ptrdiff_t difference_type;
|
typedef std::ptrdiff_t difference_type;
|
||||||
@@ -407,6 +407,8 @@ namespace unordered
|
|||||||
::boost::unordered::detail::rebind_wrap<
|
::boost::unordered::detail::rebind_wrap<
|
||||||
allocator_type, value_type>::type
|
allocator_type, value_type>::type
|
||||||
value_allocator;
|
value_allocator;
|
||||||
|
typedef ::boost::unordered::detail::allocator_traits<value_allocator>
|
||||||
|
allocator_traits;
|
||||||
|
|
||||||
typedef ::boost::unordered::detail::multimap<K, H, P,
|
typedef ::boost::unordered::detail::multimap<K, H, P,
|
||||||
value_allocator> types;
|
value_allocator> types;
|
||||||
@@ -417,13 +419,12 @@ namespace unordered
|
|||||||
public:
|
public:
|
||||||
|
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
value_allocator::pointer pointer;
|
allocator_traits::pointer pointer;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
value_allocator::const_pointer const_pointer;
|
allocator_traits::const_pointer const_pointer;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
|
||||||
value_allocator::reference reference;
|
typedef value_type& reference;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef value_type const& const_reference;
|
||||||
value_allocator::const_reference const_reference;
|
|
||||||
|
|
||||||
typedef std::size_t size_type;
|
typedef std::size_t size_type;
|
||||||
typedef std::ptrdiff_t difference_type;
|
typedef std::ptrdiff_t difference_type;
|
||||||
|
@@ -56,6 +56,8 @@ namespace unordered
|
|||||||
::boost::unordered::detail::rebind_wrap<
|
::boost::unordered::detail::rebind_wrap<
|
||||||
allocator_type, value_type>::type
|
allocator_type, value_type>::type
|
||||||
value_allocator;
|
value_allocator;
|
||||||
|
typedef ::boost::unordered::detail::allocator_traits<value_allocator>
|
||||||
|
allocator_traits;
|
||||||
|
|
||||||
typedef ::boost::unordered::detail::set<H, P,
|
typedef ::boost::unordered::detail::set<H, P,
|
||||||
value_allocator> types;
|
value_allocator> types;
|
||||||
@@ -66,13 +68,12 @@ namespace unordered
|
|||||||
public:
|
public:
|
||||||
|
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
value_allocator::pointer pointer;
|
allocator_traits::pointer pointer;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
value_allocator::const_pointer const_pointer;
|
allocator_traits::const_pointer const_pointer;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
|
||||||
value_allocator::reference reference;
|
typedef value_type& reference;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef value_type const& const_reference;
|
||||||
value_allocator::const_reference const_reference;
|
|
||||||
|
|
||||||
typedef std::size_t size_type;
|
typedef std::size_t size_type;
|
||||||
typedef std::ptrdiff_t difference_type;
|
typedef std::ptrdiff_t difference_type;
|
||||||
@@ -387,6 +388,8 @@ namespace unordered
|
|||||||
::boost::unordered::detail::rebind_wrap<
|
::boost::unordered::detail::rebind_wrap<
|
||||||
allocator_type, value_type>::type
|
allocator_type, value_type>::type
|
||||||
value_allocator;
|
value_allocator;
|
||||||
|
typedef ::boost::unordered::detail::allocator_traits<value_allocator>
|
||||||
|
allocator_traits;
|
||||||
|
|
||||||
typedef ::boost::unordered::detail::multiset<H, P,
|
typedef ::boost::unordered::detail::multiset<H, P,
|
||||||
value_allocator> types;
|
value_allocator> types;
|
||||||
@@ -397,13 +400,12 @@ namespace unordered
|
|||||||
public:
|
public:
|
||||||
|
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
value_allocator::pointer pointer;
|
allocator_traits::pointer pointer;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef BOOST_DEDUCED_TYPENAME
|
||||||
value_allocator::const_pointer const_pointer;
|
allocator_traits::const_pointer const_pointer;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
|
||||||
value_allocator::reference reference;
|
typedef value_type& reference;
|
||||||
typedef BOOST_DEDUCED_TYPENAME
|
typedef value_type const& const_reference;
|
||||||
value_allocator::const_reference const_reference;
|
|
||||||
|
|
||||||
typedef std::size_t size_type;
|
typedef std::size_t size_type;
|
||||||
typedef std::ptrdiff_t difference_type;
|
typedef std::ptrdiff_t difference_type;
|
||||||
|
@@ -33,6 +33,7 @@ namespace minimal
|
|||||||
template <class T> class ptr;
|
template <class T> class ptr;
|
||||||
template <class T> class const_ptr;
|
template <class T> class const_ptr;
|
||||||
template <class T> class allocator;
|
template <class T> class allocator;
|
||||||
|
template <class T> class cxx11_allocator;
|
||||||
|
|
||||||
class copy_constructible
|
class copy_constructible
|
||||||
{
|
{
|
||||||
@@ -316,6 +317,69 @@ namespace minimal
|
|||||||
void swap(allocator<T>&, allocator<T>&)
|
void swap(allocator<T>&, allocator<T>&)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// C++11 allocator
|
||||||
|
//
|
||||||
|
// Not a fully minimal C++11 allocator, just what I support. Hopefully will
|
||||||
|
// cut down further in the future.
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
class cxx11_allocator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef T value_type;
|
||||||
|
template <class U> struct rebind { typedef cxx11_allocator<U> other; };
|
||||||
|
|
||||||
|
cxx11_allocator() {}
|
||||||
|
template <class Y> cxx11_allocator(cxx11_allocator<Y> const&) {}
|
||||||
|
cxx11_allocator(cxx11_allocator const&) {}
|
||||||
|
~cxx11_allocator() {}
|
||||||
|
|
||||||
|
T* address(T& r) { return &r; }
|
||||||
|
T const* address(T const& r) { return &r; }
|
||||||
|
|
||||||
|
T* allocate(std::size_t n) {
|
||||||
|
return static_cast<T*>(::operator new(n * sizeof(T)));
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class Y>
|
||||||
|
T* allocate(std::size_t n, const_ptr<Y> u) {
|
||||||
|
return static_cast<T*>(::operator new(n * sizeof(T)));
|
||||||
|
}
|
||||||
|
|
||||||
|
void deallocate(T* p, std::size_t) {
|
||||||
|
::operator delete((void*) p);
|
||||||
|
}
|
||||||
|
|
||||||
|
void construct(T* p, T const& t) { new((void*)p) T(t); }
|
||||||
|
|
||||||
|
#if defined(BOOST_UNORDERED_STD_FORWARD_MOVE)
|
||||||
|
template<class... Args> void construct(T* p, Args&&... args) {
|
||||||
|
new((void*)p) T(std::forward<Args>(args)...);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
void destroy(T* p) { p->~T(); }
|
||||||
|
|
||||||
|
std::size_t max_size() const { return 1000u; }
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
inline bool operator==(cxx11_allocator<T> const&, cxx11_allocator<T> const&)
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
inline bool operator!=(cxx11_allocator<T> const&, cxx11_allocator<T> const&)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
void swap(cxx11_allocator<T>&, cxx11_allocator<T>&)
|
||||||
|
{
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -17,6 +17,19 @@
|
|||||||
|
|
||||||
// Explicit instantiation to catch compile-time errors
|
// Explicit instantiation to catch compile-time errors
|
||||||
|
|
||||||
|
template class boost::unordered_map<
|
||||||
|
int,
|
||||||
|
int,
|
||||||
|
boost::hash<int>,
|
||||||
|
std::equal_to<int>,
|
||||||
|
test::minimal::allocator<std::pair<int const, int> > >;
|
||||||
|
template class boost::unordered_multimap<
|
||||||
|
int,
|
||||||
|
int,
|
||||||
|
boost::hash<int>,
|
||||||
|
std::equal_to<int>,
|
||||||
|
test::minimal::allocator<std::pair<int const, int> > >;
|
||||||
|
|
||||||
template class boost::unordered_map<
|
template class boost::unordered_map<
|
||||||
test::minimal::assignable,
|
test::minimal::assignable,
|
||||||
test::minimal::default_copy_constructible,
|
test::minimal::default_copy_constructible,
|
||||||
@@ -42,6 +55,11 @@ UNORDERED_AUTO_TEST(test0)
|
|||||||
|
|
||||||
boost::unordered_map<int, int> int_map;
|
boost::unordered_map<int, int> int_map;
|
||||||
|
|
||||||
|
boost::unordered_map<int, int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<std::pair<int const, int> >
|
||||||
|
> int_map2;
|
||||||
|
|
||||||
boost::unordered_map<
|
boost::unordered_map<
|
||||||
test::minimal::assignable,
|
test::minimal::assignable,
|
||||||
test::minimal::copy_constructible,
|
test::minimal::copy_constructible,
|
||||||
@@ -50,12 +68,18 @@ UNORDERED_AUTO_TEST(test0)
|
|||||||
test::minimal::allocator<value_type> > map;
|
test::minimal::allocator<value_type> > map;
|
||||||
|
|
||||||
container_test(int_map, std::pair<int const, int>(0, 0));
|
container_test(int_map, std::pair<int const, int>(0, 0));
|
||||||
|
container_test(int_map2, std::pair<int const, int>(0, 0));
|
||||||
container_test(map, value);
|
container_test(map, value);
|
||||||
|
|
||||||
std::cout<<"Test unordered_multimap.\n";
|
std::cout<<"Test unordered_multimap.\n";
|
||||||
|
|
||||||
boost::unordered_multimap<int, int> int_multimap;
|
boost::unordered_multimap<int, int> int_multimap;
|
||||||
|
|
||||||
|
boost::unordered_multimap<int, int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<std::pair<int const, int> >
|
||||||
|
> int_multimap2;
|
||||||
|
|
||||||
boost::unordered_multimap<
|
boost::unordered_multimap<
|
||||||
test::minimal::assignable,
|
test::minimal::assignable,
|
||||||
test::minimal::copy_constructible,
|
test::minimal::copy_constructible,
|
||||||
@@ -64,6 +88,7 @@ UNORDERED_AUTO_TEST(test0)
|
|||||||
test::minimal::allocator<value_type> > multimap;
|
test::minimal::allocator<value_type> > multimap;
|
||||||
|
|
||||||
container_test(int_multimap, std::pair<int const, int>(0, 0));
|
container_test(int_multimap, std::pair<int const, int>(0, 0));
|
||||||
|
container_test(int_multimap2, std::pair<int const, int>(0, 0));
|
||||||
container_test(multimap, value);
|
container_test(multimap, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -74,6 +99,11 @@ UNORDERED_AUTO_TEST(equality_tests) {
|
|||||||
|
|
||||||
boost::unordered_map<int, int> int_map;
|
boost::unordered_map<int, int> int_map;
|
||||||
|
|
||||||
|
boost::unordered_map<int, int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<std::pair<int const, int> >
|
||||||
|
> int_map2;
|
||||||
|
|
||||||
boost::unordered_map<
|
boost::unordered_map<
|
||||||
test::minimal::copy_constructible_equality_comparable,
|
test::minimal::copy_constructible_equality_comparable,
|
||||||
test::minimal::copy_constructible_equality_comparable,
|
test::minimal::copy_constructible_equality_comparable,
|
||||||
@@ -82,10 +112,16 @@ UNORDERED_AUTO_TEST(equality_tests) {
|
|||||||
test::minimal::allocator<value_type> > map;
|
test::minimal::allocator<value_type> > map;
|
||||||
|
|
||||||
equality_test(int_map);
|
equality_test(int_map);
|
||||||
|
equality_test(int_map2);
|
||||||
equality_test(map);
|
equality_test(map);
|
||||||
|
|
||||||
boost::unordered_multimap<int, int> int_multimap;
|
boost::unordered_multimap<int, int> int_multimap;
|
||||||
|
|
||||||
|
boost::unordered_multimap<int, int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<std::pair<int const, int> >
|
||||||
|
> int_multimap2;
|
||||||
|
|
||||||
boost::unordered_multimap<
|
boost::unordered_multimap<
|
||||||
test::minimal::copy_constructible_equality_comparable,
|
test::minimal::copy_constructible_equality_comparable,
|
||||||
test::minimal::copy_constructible_equality_comparable,
|
test::minimal::copy_constructible_equality_comparable,
|
||||||
@@ -94,6 +130,7 @@ UNORDERED_AUTO_TEST(equality_tests) {
|
|||||||
test::minimal::allocator<value_type> > multimap;
|
test::minimal::allocator<value_type> > multimap;
|
||||||
|
|
||||||
equality_test(int_multimap);
|
equality_test(int_multimap);
|
||||||
|
equality_test(int_multimap2);
|
||||||
equality_test(multimap);
|
equality_test(multimap);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -107,18 +144,37 @@ UNORDERED_AUTO_TEST(test1) {
|
|||||||
|
|
||||||
boost::unordered_map<int, int> map;
|
boost::unordered_map<int, int> map;
|
||||||
|
|
||||||
|
boost::unordered_map<int, int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<std::pair<int const, int> >
|
||||||
|
> map2;
|
||||||
|
|
||||||
unordered_unique_test(map, map_value);
|
unordered_unique_test(map, map_value);
|
||||||
unordered_map_test(map, value, value);
|
unordered_map_test(map, value, value);
|
||||||
unordered_test(map, value, map_value, hash, equal_to);
|
unordered_test(map, value, map_value, hash, equal_to);
|
||||||
unordered_map_functions(map, value, value);
|
unordered_map_functions(map, value, value);
|
||||||
|
|
||||||
|
unordered_unique_test(map2, map_value);
|
||||||
|
unordered_map_test(map2, value, value);
|
||||||
|
unordered_test(map2, value, map_value, hash, equal_to);
|
||||||
|
unordered_map_functions(map2, value, value);
|
||||||
|
|
||||||
std::cout<<"Test unordered_multimap.\n";
|
std::cout<<"Test unordered_multimap.\n";
|
||||||
|
|
||||||
boost::unordered_multimap<int, int> multimap;
|
boost::unordered_multimap<int, int> multimap;
|
||||||
|
|
||||||
|
boost::unordered_multimap<int, int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<std::pair<int const, int> >
|
||||||
|
> multimap2;
|
||||||
|
|
||||||
unordered_equivalent_test(multimap, map_value);
|
unordered_equivalent_test(multimap, map_value);
|
||||||
unordered_map_test(multimap, value, value);
|
unordered_map_test(multimap, value, value);
|
||||||
unordered_test(multimap, value, map_value, hash, equal_to);
|
unordered_test(multimap, value, map_value, hash, equal_to);
|
||||||
|
|
||||||
|
unordered_equivalent_test(multimap2, map_value);
|
||||||
|
unordered_map_test(multimap2, value, value);
|
||||||
|
unordered_test(multimap2, value, map_value, hash, equal_to);
|
||||||
}
|
}
|
||||||
|
|
||||||
UNORDERED_AUTO_TEST(test2)
|
UNORDERED_AUTO_TEST(test2)
|
||||||
@@ -149,7 +205,6 @@ UNORDERED_AUTO_TEST(test2)
|
|||||||
unordered_map_test(map, assignable, copy_constructible);
|
unordered_map_test(map, assignable, copy_constructible);
|
||||||
unordered_test(map, assignable, map_value, hash, equal_to);
|
unordered_test(map, assignable, map_value, hash, equal_to);
|
||||||
|
|
||||||
|
|
||||||
boost::unordered_map<
|
boost::unordered_map<
|
||||||
test::minimal::assignable,
|
test::minimal::assignable,
|
||||||
test::minimal::default_copy_constructible,
|
test::minimal::default_copy_constructible,
|
||||||
|
@@ -16,7 +16,18 @@
|
|||||||
#include "./compile_tests.hpp"
|
#include "./compile_tests.hpp"
|
||||||
|
|
||||||
// Explicit instantiation to catch compile-time errors
|
// Explicit instantiation to catch compile-time errors
|
||||||
|
/*
|
||||||
|
template class boost::unordered_set<
|
||||||
|
int,
|
||||||
|
boost::hash<int>,
|
||||||
|
std::equal_to<int>,
|
||||||
|
test::minimal::allocator<int> >;
|
||||||
|
template class boost::unordered_multiset<
|
||||||
|
int,
|
||||||
|
boost::hash<int>,
|
||||||
|
std::equal_to<int>,
|
||||||
|
test::minimal::allocator<int> >;
|
||||||
|
*/
|
||||||
template class boost::unordered_set<
|
template class boost::unordered_set<
|
||||||
test::minimal::assignable,
|
test::minimal::assignable,
|
||||||
test::minimal::hash<test::minimal::assignable>,
|
test::minimal::hash<test::minimal::assignable>,
|
||||||
@@ -33,7 +44,14 @@ UNORDERED_AUTO_TEST(test0)
|
|||||||
test::minimal::assignable assignable = test::minimal::assignable::create();
|
test::minimal::assignable assignable = test::minimal::assignable::create();
|
||||||
|
|
||||||
std::cout<<"Test unordered_set.\n";
|
std::cout<<"Test unordered_set.\n";
|
||||||
|
|
||||||
boost::unordered_set<int> int_set;
|
boost::unordered_set<int> int_set;
|
||||||
|
|
||||||
|
boost::unordered_set<int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<int>
|
||||||
|
> int_set2;
|
||||||
|
|
||||||
boost::unordered_set<
|
boost::unordered_set<
|
||||||
test::minimal::assignable,
|
test::minimal::assignable,
|
||||||
test::minimal::hash<test::minimal::assignable>,
|
test::minimal::hash<test::minimal::assignable>,
|
||||||
@@ -41,10 +59,18 @@ UNORDERED_AUTO_TEST(test0)
|
|||||||
test::minimal::allocator<test::minimal::assignable> > set;
|
test::minimal::allocator<test::minimal::assignable> > set;
|
||||||
|
|
||||||
container_test(int_set, 0);
|
container_test(int_set, 0);
|
||||||
|
container_test(int_set2, 0);
|
||||||
container_test(set, assignable);
|
container_test(set, assignable);
|
||||||
|
|
||||||
std::cout<<"Test unordered_multiset.\n";
|
std::cout<<"Test unordered_multiset.\n";
|
||||||
|
|
||||||
boost::unordered_multiset<int> int_multiset;
|
boost::unordered_multiset<int> int_multiset;
|
||||||
|
|
||||||
|
boost::unordered_multiset<int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<int>
|
||||||
|
> int_multiset2;
|
||||||
|
|
||||||
boost::unordered_multiset<
|
boost::unordered_multiset<
|
||||||
test::minimal::assignable,
|
test::minimal::assignable,
|
||||||
test::minimal::hash<test::minimal::assignable>,
|
test::minimal::hash<test::minimal::assignable>,
|
||||||
@@ -52,6 +78,7 @@ UNORDERED_AUTO_TEST(test0)
|
|||||||
test::minimal::allocator<test::minimal::assignable> > multiset;
|
test::minimal::allocator<test::minimal::assignable> > multiset;
|
||||||
|
|
||||||
container_test(int_multiset, 0);
|
container_test(int_multiset, 0);
|
||||||
|
container_test(int_multiset2, 0);
|
||||||
container_test(multiset, assignable);
|
container_test(multiset, assignable);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -60,6 +87,11 @@ UNORDERED_AUTO_TEST(equality_tests) {
|
|||||||
|
|
||||||
boost::unordered_set<int> int_set;
|
boost::unordered_set<int> int_set;
|
||||||
|
|
||||||
|
boost::unordered_set<int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<int>
|
||||||
|
> int_set2;
|
||||||
|
|
||||||
boost::unordered_set<
|
boost::unordered_set<
|
||||||
test::minimal::copy_constructible_equality_comparable,
|
test::minimal::copy_constructible_equality_comparable,
|
||||||
test::minimal::hash<test::minimal::copy_constructible_equality_comparable>,
|
test::minimal::hash<test::minimal::copy_constructible_equality_comparable>,
|
||||||
@@ -67,10 +99,16 @@ UNORDERED_AUTO_TEST(equality_tests) {
|
|||||||
test::minimal::allocator<value_type> > set;
|
test::minimal::allocator<value_type> > set;
|
||||||
|
|
||||||
equality_test(int_set);
|
equality_test(int_set);
|
||||||
|
equality_test(int_set2);
|
||||||
equality_test(set);
|
equality_test(set);
|
||||||
|
|
||||||
boost::unordered_multiset<int> int_multiset;
|
boost::unordered_multiset<int> int_multiset;
|
||||||
|
|
||||||
|
boost::unordered_multiset<int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<int>
|
||||||
|
> int_multiset2;
|
||||||
|
|
||||||
boost::unordered_multiset<
|
boost::unordered_multiset<
|
||||||
test::minimal::copy_constructible_equality_comparable,
|
test::minimal::copy_constructible_equality_comparable,
|
||||||
test::minimal::hash<test::minimal::copy_constructible_equality_comparable>,
|
test::minimal::hash<test::minimal::copy_constructible_equality_comparable>,
|
||||||
@@ -78,6 +116,7 @@ UNORDERED_AUTO_TEST(equality_tests) {
|
|||||||
test::minimal::allocator<value_type> > multiset;
|
test::minimal::allocator<value_type> > multiset;
|
||||||
|
|
||||||
equality_test(int_multiset);
|
equality_test(int_multiset);
|
||||||
|
equality_test(int_multiset2);
|
||||||
equality_test(multiset);
|
equality_test(multiset);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -91,17 +130,35 @@ UNORDERED_AUTO_TEST(test1)
|
|||||||
|
|
||||||
boost::unordered_set<int> set;
|
boost::unordered_set<int> set;
|
||||||
|
|
||||||
|
boost::unordered_set<int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<int>
|
||||||
|
> set2;
|
||||||
|
|
||||||
unordered_unique_test(set, value);
|
unordered_unique_test(set, value);
|
||||||
unordered_set_test(set, value);
|
unordered_set_test(set, value);
|
||||||
unordered_test(set, value, value, hash, equal_to);
|
unordered_test(set, value, value, hash, equal_to);
|
||||||
|
|
||||||
|
unordered_unique_test(set2, value);
|
||||||
|
unordered_set_test(set2, value);
|
||||||
|
unordered_test(set2, value, value, hash, equal_to);
|
||||||
|
|
||||||
std::cout<<"Test unordered_multiset.\n";
|
std::cout<<"Test unordered_multiset.\n";
|
||||||
|
|
||||||
boost::unordered_multiset<int> multiset;
|
boost::unordered_multiset<int> multiset;
|
||||||
|
|
||||||
|
boost::unordered_multiset<int,
|
||||||
|
boost::hash<int>, std::equal_to<int>,
|
||||||
|
test::minimal::cxx11_allocator<int>
|
||||||
|
> multiset2;
|
||||||
|
|
||||||
unordered_equivalent_test(multiset, value);
|
unordered_equivalent_test(multiset, value);
|
||||||
unordered_set_test(multiset, value);
|
unordered_set_test(multiset, value);
|
||||||
unordered_test(multiset, value, value, hash, equal_to);
|
unordered_test(multiset, value, value, hash, equal_to);
|
||||||
|
|
||||||
|
unordered_equivalent_test(multiset2, value);
|
||||||
|
unordered_set_test(multiset2, value);
|
||||||
|
unordered_test(multiset2, value, value, hash, equal_to);
|
||||||
}
|
}
|
||||||
|
|
||||||
UNORDERED_AUTO_TEST(test2)
|
UNORDERED_AUTO_TEST(test2)
|
||||||
|
Reference in New Issue
Block a user