Add const cast for piecewise construction

This commit is contained in:
Daniel James
2016-10-22 09:42:56 +01:00
parent dad0d48c9c
commit ad2256b13c
2 changed files with 25 additions and 12 deletions

View File

@@ -88,6 +88,16 @@ namespace boost { namespace unordered { namespace detail {
convert_from_anything(T const&); convert_from_anything(T const&);
}; };
namespace func {
// This is a bit nasty, when constructing the individual members
// of a std::pair, need to cast away 'const'. For modern compilers,
// should be able to use std::piecewise_construct instead.
template <typename T> T* const_cast_pointer(T* x) { return x; }
template <typename T> T* const_cast_pointer(T const* x) {
return const_cast<T*>(x);
}
}
//////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////
// emplace_args // emplace_args
// //
@@ -1104,9 +1114,13 @@ BOOST_UNORDERED_CONSTRUCT_FROM_TUPLE(10, boost::)
BOOST_FWD_REF(A0), BOOST_FWD_REF(A1) a1, BOOST_FWD_REF(A2) a2) BOOST_FWD_REF(A0), BOOST_FWD_REF(A1) a1, BOOST_FWD_REF(A2) a2)
{ {
boost::unordered::detail::func::construct_from_tuple(alloc, boost::unordered::detail::func::construct_from_tuple(alloc,
boost::addressof(address->first), boost::forward<A1>(a1)); boost::unordered::detail::func::const_cast_pointer(
boost::addressof(address->first)),
boost::forward<A1>(a1));
boost::unordered::detail::func::construct_from_tuple(alloc, boost::unordered::detail::func::construct_from_tuple(alloc,
boost::addressof(address->second), boost::forward<A2>(a2)); boost::unordered::detail::func::const_cast_pointer(
boost::addressof(address->second)),
boost::forward<A2>(a2));
} }
#else // BOOST_NO_CXX11_VARIADIC_TEMPLATES #else // BOOST_NO_CXX11_VARIADIC_TEMPLATES
@@ -1176,9 +1190,13 @@ BOOST_UNORDERED_CONSTRUCT_FROM_TUPLE(10, boost::)
typename enable_if<use_piecewise<A0>, void*>::type = 0) typename enable_if<use_piecewise<A0>, void*>::type = 0)
{ {
boost::unordered::detail::func::construct_from_tuple(alloc, boost::unordered::detail::func::construct_from_tuple(alloc,
boost::addressof(address->first), args.a1); boost::unordered::detail::func::const_cast_pointer(
boost::addressof(address->first)),
args.a1);
boost::unordered::detail::func::construct_from_tuple(alloc, boost::unordered::detail::func::construct_from_tuple(alloc,
boost::addressof(address->second), args.a2); boost::unordered::detail::func::const_cast_pointer(
boost::addressof(address->second)),
args.a2);
} }
#endif // BOOST_NO_CXX11_VARIADIC_TEMPLATES #endif // BOOST_NO_CXX11_VARIADIC_TEMPLATES
@@ -1331,14 +1349,6 @@ namespace boost { namespace unordered { namespace detail { namespace func {
return a.release(); return a.release();
} }
// This is a bit nasty, when constructing the individual members
// of a std::pair, need to cast away 'const'. For modern compilers,
// should be able to use std::piecewise_construct instead.
template <typename T> T* const_cast_pointer(T* x) { return x; }
template <typename T> T* const_cast_pointer(T const* x) {
return const_cast<T*>(x);
}
// TODO: When possible, it might be better to use std::pair's // TODO: When possible, it might be better to use std::pair's
// constructor for std::piece_construct with std::tuple. // constructor for std::piece_construct with std::tuple.
template <typename Alloc, typename Key> template <typename Alloc, typename Key>

View File

@@ -247,6 +247,9 @@ void unordered_map_test(X& r, Key const& k, T const& v)
r.emplace(k, v); r.emplace(k, v);
r.emplace(k_lvalue, v_lvalue); r.emplace(k_lvalue, v_lvalue);
r.emplace(rvalue(k), rvalue(v)); r.emplace(rvalue(k), rvalue(v));
r.emplace(boost::unordered::piecewise_construct,
boost::make_tuple(k), boost::make_tuple(v));
} }
template <class X> template <class X>