Add forwarding rvalue-ref 2-arg constructors.

This commit is contained in:
jzmaddock
2021-09-20 20:00:12 +01:00
parent 7d94c9c61f
commit 43f8469f20
3 changed files with 67 additions and 0 deletions
@@ -1548,8 +1548,12 @@ BOOST_MP_CXX14_CONSTEXPR void check_shift_range(V, const std::integral_constant<
template <class T>
BOOST_MP_CXX14_CONSTEXPR const T& evaluate_if_expression(const T& val) { return val; }
template <class T>
BOOST_MP_CXX14_CONSTEXPR T&& evaluate_if_expression(T&& val) { return static_cast<T&&>(val); }
template <class tag, class Arg1, class Arg2, class Arg3, class Arg4>
BOOST_MP_CXX14_CONSTEXPR typename expression<tag, Arg1, Arg2, Arg3, Arg4>::result_type evaluate_if_expression(const expression<tag, Arg1, Arg2, Arg3, Arg4>& val) { return val; }
template <class tag, class Arg1, class Arg2, class Arg3, class Arg4>
BOOST_MP_CXX14_CONSTEXPR typename expression<tag, Arg1, Arg2, Arg3, Arg4>::result_type evaluate_if_expression(expression<tag, Arg1, Arg2, Arg3, Arg4>&& val) { return val; }
} // namespace detail
+30
View File
@@ -2189,6 +2189,17 @@ struct gmp_rational
mpq_canonicalize(m_data);
j.data()[0]._mp_d = nullptr;
}
template <class U>
gmp_rational(gmp_int&& a, const U& b, typename std::enable_if<std::is_constructible<gmp_int, U>::value>::type* = nullptr)
{
gmp_int j(b);
m_data[0]._mp_num = a.data()[0];
m_data[0]._mp_den = j.data()[0];
if (boost::multiprecision::detail::unsigned_abs(b) > 1)
mpq_canonicalize(m_data);
a.data()[0]._mp_d = nullptr;
j.data()[0]._mp_d = nullptr;
}
template <class T>
gmp_rational(const T& a, const gmp_int& b, typename std::enable_if<std::is_constructible<gmp_int, T>::value>::type* = nullptr)
{
@@ -2199,12 +2210,31 @@ struct gmp_rational
mpq_canonicalize(m_data);
i.data()[0]._mp_d = nullptr;
}
template <class T>
gmp_rational(const T& a, gmp_int&& b, typename std::enable_if<std::is_constructible<gmp_int, T>::value>::type* = nullptr)
{
gmp_int i(a);
m_data[0]._mp_num = i.data()[0];
m_data[0]._mp_den = b.data()[0];
if(boost::multiprecision::detail::unsigned_abs(a) > 1)
mpq_canonicalize(m_data);
i.data()[0]._mp_d = nullptr;
b.data()[0]._mp_d = nullptr;
}
gmp_rational(const gmp_int& a, const gmp_int& b)
{
mpz_init_set(&m_data[0]._mp_num, a.data());
mpz_init_set(&m_data[0]._mp_den, b.data());
mpq_canonicalize(m_data);
}
gmp_rational(gmp_int&& a, gmp_int&& b)
{
m_data[0]._mp_num = a.data()[0];
m_data[0]._mp_den = b.data()[0];
mpq_canonicalize(m_data);
a.data()[0]._mp_d = nullptr;
b.data()[0]._mp_d = nullptr;
}
// rvalue copy
gmp_rational(gmp_rational&& o) noexcept
{
+33
View File
@@ -164,6 +164,39 @@ class number
{
}
template <class V, class U>
BOOST_MP_FORCEINLINE BOOST_MP_CXX14_CONSTEXPR number(V&& v1, const U& v2,
typename std::enable_if<
(std::is_convertible<V, value_type>::value
&& std::is_convertible<U, value_type>::value
&& !std::is_same<value_type, self_type>::value
&& std::is_constructible<Backend, typename detail::canonical<Backend, decltype(detail::evaluate_if_expression(std::declval<const V&>()))>::type const&, typename detail::canonical<Backend, decltype(detail::evaluate_if_expression(std::declval<const U&>()))>::type const&>::value
&& !boost::multiprecision::detail::is_variable_precision<Backend>::value)>::type* = 0)
: m_backend(canonical_value(detail::evaluate_if_expression(static_cast<V&&>(v1))), canonical_value(detail::evaluate_if_expression(v2)))
{
}
template <class V, class U>
BOOST_MP_FORCEINLINE BOOST_MP_CXX14_CONSTEXPR number(const V& v1, U&& v2,
typename std::enable_if<
(std::is_convertible<V, value_type>::value
&& std::is_convertible<U, value_type>::value
&& !std::is_same<value_type, self_type>::value
&& std::is_constructible<Backend, typename detail::canonical<Backend, decltype(detail::evaluate_if_expression(std::declval<const V&>()))>::type const&, typename detail::canonical<Backend, decltype(detail::evaluate_if_expression(std::declval<const U&>()))>::type const&>::value
&& !boost::multiprecision::detail::is_variable_precision<Backend>::value)>::type* = 0)
: m_backend(canonical_value(detail::evaluate_if_expression(v1)), canonical_value(detail::evaluate_if_expression(static_cast<U&&>(v2))))
{
}
template <class V, class U>
BOOST_MP_FORCEINLINE BOOST_MP_CXX14_CONSTEXPR number(V&& v1, U&& v2,
typename std::enable_if<
(std::is_convertible<V, value_type>::value
&& std::is_convertible<U, value_type>::value
&& !std::is_same<value_type, self_type>::value
&& std::is_constructible<Backend, typename detail::canonical<Backend, decltype(detail::evaluate_if_expression(std::declval<const V&>()))>::type const&, typename detail::canonical<Backend, decltype(detail::evaluate_if_expression(std::declval<const U&>()))>::type const&>::value
&& !boost::multiprecision::detail::is_variable_precision<Backend>::value)>::type* = 0)
: m_backend(canonical_value(detail::evaluate_if_expression(static_cast<V&&>(v1))), canonical_value(detail::evaluate_if_expression(static_cast<U&&>(v2))))
{
}
template <class V, class U>
BOOST_MP_FORCEINLINE BOOST_MP_CXX14_CONSTEXPR number(const V& v1, const U& v2,
typename std::enable_if<
(std::is_convertible<V, value_type>::value