|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r73805 - trunk/boost/unordered/detail
From: dnljms_at_[hidden]
Date: 2011-08-15 17:34:02
Author: danieljames
Date: 2011-08-15 17:34:01 EDT (Mon, 15 Aug 2011)
New Revision: 73805
URL: http://svn.boost.org/trac/boost/changeset/73805
Log:
Unordered: Support moving allocators.
Text files modified:
trunk/boost/unordered/detail/buckets.hpp | 14 ++---
trunk/boost/unordered/detail/table.hpp | 4
trunk/boost/unordered/detail/util.hpp | 99 +++++++++++++++++++++++++++++++++++++++
3 files changed, 106 insertions(+), 11 deletions(-)
Modified: trunk/boost/unordered/detail/buckets.hpp
==============================================================================
--- trunk/boost/unordered/detail/buckets.hpp (original)
+++ trunk/boost/unordered/detail/buckets.hpp 2011-08-15 17:34:01 EDT (Mon, 15 Aug 2011)
@@ -65,7 +65,7 @@
bucket_ptr buckets_;
std::size_t bucket_count_;
std::size_t size_;
- ::boost::compressed_pair<bucket_allocator, node_allocator> allocators_;
+ compressed_pair<bucket_allocator, node_allocator> allocators_;
// Data access
@@ -106,22 +106,20 @@
{
}
- // TODO: Need to move allocators_, not copy. But compressed_pair
- // doesn't support move parameters.
- buckets(buckets& b, move_tag)
+ buckets(buckets& b, move_tag m)
: buckets_(),
bucket_count_(b.bucket_count_),
size_(),
- allocators_(b.allocators_)
+ allocators_(b.allocators_, m)
{
swap(b);
}
template <typename T>
- buckets(table<T>& x, move_tag)
+ buckets(table<T>& x, move_tag m)
: buckets_(),
bucket_count_(x.bucket_count_),
- allocators_(x.allocators_)
+ allocators_(x.allocators_, m)
{
swap(x);
x.size_ = 0;
@@ -424,7 +422,7 @@
friend class set_hash_functions<H, P>;
functions& operator=(functions const&);
- typedef ::boost::compressed_pair<H, P> function_pair;
+ typedef compressed_pair<H, P> function_pair;
typedef BOOST_DEDUCED_TYPENAME ::boost::aligned_storage<
sizeof(function_pair),
::boost::alignment_of<function_pair>::value>::type aligned_function;
Modified: trunk/boost/unordered/detail/table.hpp
==============================================================================
--- trunk/boost/unordered/detail/table.hpp (original)
+++ trunk/boost/unordered/detail/table.hpp 2011-08-15 17:34:01 EDT (Mon, 15 Aug 2011)
@@ -245,7 +245,7 @@
// aren't deleted with the wrong allocator.
if(this->buckets_) this->delete_buckets();
// TODO: Can allocator assignment throw?
- this->allocators_ = x.allocators_;
+ this->allocators_.assign(x.allocators_);
this->swap(tmp, false_type());
}
@@ -259,7 +259,7 @@
void move_assign(table& x, true_type)
{
if(this->buckets_) this->delete_buckets();
- this->allocators_ = x.allocators_; // TODO: Move allocators, not copy.
+ this->allocators_.move_assign(x.allocators_);
move_assign_no_alloc(x);
}
Modified: trunk/boost/unordered/detail/util.hpp
==============================================================================
--- trunk/boost/unordered/detail/util.hpp (original)
+++ trunk/boost/unordered/detail/util.hpp 2011-08-15 17:34:01 EDT (Mon, 15 Aug 2011)
@@ -19,16 +19,17 @@
#include <boost/assert.hpp>
#include <boost/iterator.hpp>
#include <boost/iterator/iterator_categories.hpp>
-#include <boost/compressed_pair.hpp>
#include <boost/type_traits/aligned_storage.hpp>
#include <boost/type_traits/alignment_of.hpp>
#include <boost/type_traits/remove_const.hpp>
+#include <boost/type_traits/is_empty.hpp>
#include <boost/throw_exception.hpp>
#include <boost/unordered/detail/allocator_helpers.hpp>
#include <boost/preprocessor/seq/size.hpp>
#include <boost/preprocessor/seq/enum.hpp>
#include <boost/preprocessor/repetition/enum.hpp>
#include <boost/move/move.hpp>
+#include <boost/swap.hpp>
// Template parameters:
//
@@ -253,6 +254,102 @@
return (std::max)(static_cast<std::size_t>(insert_size(i, j)) + 1,
num_buckets);
}
+
+ ////////////////////////////////////////////////////////////////////////////
+ // compressed_pair
+
+ template <typename T, int Index>
+ struct compressed_base : private T
+ {
+ compressed_base(T const& x) : T(x) {}
+ compressed_base(T& x, move_tag) : T(boost::move(x)) {}
+
+ T& get() { return *this; }
+ T const& get() const { return *this; }
+ };
+
+ template <typename T, int Index>
+ struct uncompressed_base
+ {
+ uncompressed_base(T const& x) : value_(x) {}
+ uncompressed_base(T& x, move_tag) : value_(boost::move(x)) {}
+
+ T& get() { return value_; }
+ T const& get() const { return value_; }
+ private:
+ T value_;
+ };
+
+ template <typename T, int Index>
+ struct generate_base
+ : boost::detail::if_true<
+ boost::is_empty<T>::value
+ >:: BOOST_NESTED_TEMPLATE then<
+ compressed_base<T, Index>,
+ uncompressed_base<T, Index>
+ >
+ {};
+
+ template <typename T1, typename T2>
+ struct compressed_pair
+ : private generate_base<T1, 1>::type,
+ private generate_base<T2, 2>::type
+ {
+ typedef BOOST_DEDUCED_TYPENAME generate_base<T1, 1>::type base1;
+ typedef BOOST_DEDUCED_TYPENAME generate_base<T2, 2>::type base2;
+
+ typedef T1 first_type;
+ typedef T2 second_type;
+
+ first_type& first() {
+ return static_cast<base1*>(this)->get();
+ }
+
+ first_type const& first() const {
+ return static_cast<base1 const*>(this)->get();
+ }
+
+ second_type& second() {
+ return static_cast<base2*>(this)->get();
+ }
+
+ second_type const& second() const {
+ return static_cast<base2 const*>(this)->get();
+ }
+
+ template <typename First, typename Second>
+ compressed_pair(First const& x1, Second const& x2)
+ : base1(x1), base2(x2) {}
+
+ compressed_pair(compressed_pair const& x)
+ : base1(x.first()), base2(x.second()) {}
+
+ compressed_pair(compressed_pair& x, move_tag m)
+ : base1(x.first(), m), base2(x.second(), m) {}
+
+ void assign(compressed_pair const& x)
+ {
+ first() = x.first();
+ second() = x.second();
+ }
+
+ void move_assign(compressed_pair& x)
+ {
+ first() = boost::move(x.first());
+ second() = boost::move(x.second());
+ }
+
+ void swap(compressed_pair& x)
+ {
+ boost::swap(first(), x.first());
+ boost::swap(second(), x.second());
+ }
+
+ private:
+ // Prevent assignment just to make use of assign or
+ // move_assign explicit.
+ compressed_pair& operator=(compressed_pair const&);
+ };
}}}
#endif
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk