提升整数模数用法

问题描述 投票:0回答:1

Boost 文档提到了

integer_modulus
函数。

template <class Integer1, class Integer2>
Integer2 integer_modulus(const Integer1& x, Integer2 val);

我发现它位于 boost::multiprecision 命名空间中的

boost/multi precision/integer.hpp
中。但是,我不知道如何让它发挥作用。我尝试了不同的编译器,但在编译阶段遇到了相同的
no matching
possible candidates
错误。例子是这里

#include <iostream>
#include <boost/multiprecision/integer.hpp>
#include <boost/multiprecision/cpp_int.hpp>

namespace mp = boost::multiprecision;
using bigint_t = mp::int256_t;

int main() {
  bigint_t a = -28;
  bigint_t b = 10;
  bigint_t c = mp::integer_modulus(a, b);
  std::cout << (a % b) << std::endl;
  std::cout << c << std::endl;

  return 0;
}

错误:

<source>: In function 'int main()':
<source>:11:35: error: no matching function for call to 'integer_modulus(bigint_t&, bigint_t&)'
   11 |   bigint_t c = mp::integer_modulus(a, b);
      |                ~~~~~~~~~~~~~~~~~~~^~~~~~
In file included from /opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/cpp_int.hpp:20,
                 from /opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp:11,
                 from <source>:2:
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:155:1: note: candidate: 'template<class Backend, boost::multiprecision::expression_template_option ExpressionTemplates, class Integer> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<I>::value && (boost::multiprecision::number_category<Num>::value == boost::multiprecision::number_kind_integer)), Integer>::type boost::multiprecision::integer_modulus(const number<Backend, ExpressionTemplates>&, Integer)'
  155 | integer_modulus(const number<Backend, ExpressionTemplates>& x, Integer val)
      | ^~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:155:1: note:   template argument deduction/substitution failed:
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp: In substitution of 'template<class Backend, boost::multiprecision::expression_template_option ExpressionTemplates, class Integer> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<I>::value && (boost::multiprecision::number_category<Num>::value == boost::multiprecision::number_kind_integer)), Integer>::type boost::multiprecision::integer_modulus(const number<Backend, ExpressionTemplates>&, Integer) [with Backend = boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void>; boost::multiprecision::expression_template_option ExpressionTemplates = boost::multiprecision::et_off; Integer = boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> >]':
<source>:11:35:   required from here
   11 |   bigint_t c = mp::integer_modulus(a, b);
      |                ~~~~~~~~~~~~~~~~~~~^~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:155:1: error: no type named 'type' in 'struct std::enable_if<false, boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> > >'
  155 | integer_modulus(const number<Backend, ExpressionTemplates>& x, Integer val)
      | ^~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:163:1: note: candidate: 'template<class tag, class A1, class A2, class A3, class A4, class Integer> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<I>::value && (boost::multiprecision::number_category<typename boost::multiprecision::detail::expression<tag, Arg1, Arg2, Arg3, Arg4>::result_type>::value == boost::multiprecision::number_kind_integer)), Integer>::type boost::multiprecision::integer_modulus(const detail::expression<tag, Arg1, Arg2, Arg3, Arg4>&, Integer)'
  163 | integer_modulus(const multiprecision::detail::expression<tag, A1, A2, A3, A4>& x, Integer val)
      | ^~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:163:1: note:   template argument deduction/substitution failed:
<source>:11:35: note:   'bigint_t' {aka 'boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> >'} is not derived from 'const boost::multiprecision::detail::expression<tag, Arg1, Arg2, Arg3, Arg4>'
   11 |   bigint_t c = mp::integer_modulus(a, b);
      |                ~~~~~~~~~~~~~~~~~~~^~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp:46:179: note: candidate: 'template<class I1, class I2> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<T>::value && boost::multiprecision::detail::is_integral<Arithmetic>::value), I2>::type boost::multiprecision::integer_modulus(const I1&, I2)'
   46 | inline BOOST_MP_CXX14_CONSTEXPR typename std::enable_if<boost::multiprecision::detail::is_integral<I1>::value && boost::multiprecision::detail::is_integral<I2>::value, I2>::type integer_modulus(const I1& x, I2 val)
      |                                                                                                                                                                                   ^~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp:46:179: note:   template argument deduction/substitution failed:
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp: In substitution of 'template<class I1, class I2> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<T>::value && boost::multiprecision::detail::is_integral<Arithmetic>::value), I2>::type boost::multiprecision::integer_modulus(const I1&, I2) [with I1 = boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> >; I2 = boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> >]':
<source>:11:35:   required from here
   11 |   bigint_t c = mp::integer_modulus(a, b);
      |                ~~~~~~~~~~~~~~~~~~~^~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp:46:179: error: no type named 'type' in 'struct std::enable_if<false, boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> > >'
   46 | inline BOOST_MP_CXX14_CONSTEXPR typename std::enable_if<boost::multiprecision::detail::is_integral<I1>::value && boost::multiprecision::detail::is_integral<I2>::value, I2>::type integer_modulus(const I1& x, I2 val)
      |                                                                                                                                                                                   ^~~~~~~~~~~~~~~
ASM generation compiler returned: 1
<source>: In function 'int main()':
<source>:11:35: error: no matching function for call to 'integer_modulus(bigint_t&, bigint_t&)'
   11 |   bigint_t c = mp::integer_modulus(a, b);
      |                ~~~~~~~~~~~~~~~~~~~^~~~~~
In file included from /opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/cpp_int.hpp:20,
                 from /opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp:11,
                 from <source>:2:
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:155:1: note: candidate: 'template<class Backend, boost::multiprecision::expression_template_option ExpressionTemplates, class Integer> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<I>::value && (boost::multiprecision::number_category<Num>::value == boost::multiprecision::number_kind_integer)), Integer>::type boost::multiprecision::integer_modulus(const number<Backend, ExpressionTemplates>&, Integer)'
  155 | integer_modulus(const number<Backend, ExpressionTemplates>& x, Integer val)
      | ^~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:155:1: note:   template argument deduction/substitution failed:
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp: In substitution of 'template<class Backend, boost::multiprecision::expression_template_option ExpressionTemplates, class Integer> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<I>::value && (boost::multiprecision::number_category<Num>::value == boost::multiprecision::number_kind_integer)), Integer>::type boost::multiprecision::integer_modulus(const number<Backend, ExpressionTemplates>&, Integer) [with Backend = boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void>; boost::multiprecision::expression_template_option ExpressionTemplates = boost::multiprecision::et_off; Integer = boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> >]':
<source>:11:35:   required from here
   11 |   bigint_t c = mp::integer_modulus(a, b);
      |                ~~~~~~~~~~~~~~~~~~~^~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:155:1: error: no type named 'type' in 'struct std::enable_if<false, boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> > >'
  155 | integer_modulus(const number<Backend, ExpressionTemplates>& x, Integer val)
      | ^~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:163:1: note: candidate: 'template<class tag, class A1, class A2, class A3, class A4, class Integer> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<I>::value && (boost::multiprecision::number_category<typename boost::multiprecision::detail::expression<tag, Arg1, Arg2, Arg3, Arg4>::result_type>::value == boost::multiprecision::number_kind_integer)), Integer>::type boost::multiprecision::integer_modulus(const detail::expression<tag, Arg1, Arg2, Arg3, Arg4>&, Integer)'
  163 | integer_modulus(const multiprecision::detail::expression<tag, A1, A2, A3, A4>& x, Integer val)
      | ^~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/detail/integer_ops.hpp:163:1: note:   template argument deduction/substitution failed:
<source>:11:35: note:   'bigint_t' {aka 'boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> >'} is not derived from 'const boost::multiprecision::detail::expression<tag, Arg1, Arg2, Arg3, Arg4>'
   11 |   bigint_t c = mp::integer_modulus(a, b);
      |                ~~~~~~~~~~~~~~~~~~~^~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp:46:179: note: candidate: 'template<class I1, class I2> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<T>::value && boost::multiprecision::detail::is_integral<Arithmetic>::value), I2>::type boost::multiprecision::integer_modulus(const I1&, I2)'
   46 | inline BOOST_MP_CXX14_CONSTEXPR typename std::enable_if<boost::multiprecision::detail::is_integral<I1>::value && boost::multiprecision::detail::is_integral<I2>::value, I2>::type integer_modulus(const I1& x, I2 val)
      |                                                                                                                                                                                   ^~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp:46:179: note:   template argument deduction/substitution failed:
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp: In substitution of 'template<class I1, class I2> constexpr typename std::enable_if<(boost::multiprecision::detail::is_integral<T>::value && boost::multiprecision::detail::is_integral<Arithmetic>::value), I2>::type boost::multiprecision::integer_modulus(const I1&, I2) [with I1 = boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> >; I2 = boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> >]':
<source>:11:35:   required from here
   11 |   bigint_t c = mp::integer_modulus(a, b);
      |                ~~~~~~~~~~~~~~~~~~~^~~~~~
/opt/compiler-explorer/libs/boost_1_85_0/boost/multiprecision/integer.hpp:46:179: error: no type named 'type' in 'struct std::enable_if<false, boost::multiprecision::number<boost::multiprecision::backends::cpp_int_backend<256, 256, boost::multiprecision::signed_magnitude, boost::multiprecision::unchecked, void> > >'
   46 | inline BOOST_MP_CXX14_CONSTEXPR typename std::enable_if<boost::multiprecision::detail::is_integral<I1>::value && boost::multiprecision::detail::is_integral<I2>::value, I2>::type integer_modulus(const I1& x, I2 val)
      |                                                                                                                                                                                   ^~~~~~~~~~~~~~~
Execution build compiler returned: 1

那么,问题是:如何让它发挥作用?

c++ boost
1个回答
0
投票

您错过了文档中的一个关键点。 在您的链接中,关键点是功能

对基本(内置)整数类型进行重载

事实上,如果你查看源代码,该函数定义为

template <class I1, class I2>
typename enable_if_c<is_integral<I1>::value && is_integral<I2>::value, I2>::type integer_modulus(const I1& x, I2 val)
{
   return static_cast<I2>(x % val);
}

正如您所看到的,它仅限于

is_integral<Type>
true
的类型。

© www.soinside.com 2019 - 2024. All rights reserved.