42# ifndef MODULAR_ARITHMETIC_H
43# define MODULAR_ARITHMETIC_H
46# include <type_traits>
71# if defined(__SIZEOF_INT128__) && !defined(_WIN32)
73# elif defined(_MSC_VER) && !defined(__clang__) && (defined(_M_X64) || defined(_M_ARM64))
75 unsigned long long hi;
76 unsigned long long lo =
_umul128(a, b, &hi);
77 unsigned long long rem;
92 if (
m - a <= a) a = a - (
m - a);
113 if (
m == 1)
return 0;
136 template <
typename T>
137 requires (std::is_integral_v<T>
and std::is_signed_v<T>)
149 y = x1 -
static_cast<T>(a / b) *
y1;
178 <<
"Modular inverse does not exist (" << a <<
" is 0 mod " <<
m <<
")";
202 <<
"Modular inverse does not exist (numbers " << a
203 <<
" and " <<
m <<
" are not coprime)";
208# if defined(__SIZEOF_INT128__) && !defined(_WIN32)
269 detail::montgomery_ctx_unchecked(
const uint64_t mod)
noexcept;
295 for (
size_t i = 0; i < 6; ++i)
325 <<
"montgomery_ctx: modulus must be > 1";
327 <<
"montgomery_ctx: modulus " <<
mod <<
" must be odd";
328 return detail::montgomery_ctx_unchecked(mod);
336 template <u
int64_t Mod>
340 static_assert(
Mod > 1,
"montgomery_ctx_for_mod: modulus must be > 1");
341 static_assert((
Mod & 1ULL) == 1ULL,
342 "montgomery_ctx_for_mod: modulus must be odd");
343 return detail::montgomery_ctx_unchecked(
Mod);
389 return t64 >= ctx.mod() ?
t64 - ctx.mod() :
t64;
394 return static_cast<uint64_t>(t % ctx.mod());
424 return mont_mul(a % ctx.mod(), ctx.r2(), ctx);
458 result =
mont_mul(result, base, ctx);
482 <<
"crt: arrays must have the same size (got " <<
rem.size()
483 <<
" vs " << mod.size() <<
")";
485 const size_t n =
rem.size();
491 for (
size_t i = 0; i < n; ++i)
494 <<
"crt: all moduli must be > 1 (got " << mod[i] <<
" at index " << i <<
")";
497 <<
"crt: product of moduli overflows uint64_t at index " << i;
502 for (
size_t i = 0; i < n; ++i)
Exception handling system with formatted messages for Aleph-w.
#define ah_overflow_error_if(C)
Throws std::overflow_error if condition holds.
#define ah_domain_error_if(C)
Throws std::domain_error if condition holds.
#define ah_invalid_argument_if(C)
Throws std::invalid_argument if condition holds.
Simple dynamic array with automatic resizing and functional operations.
__gmp_expr< T, __gmp_unary_expr< __gmp_expr< T, U >, __gmp_y1_function > > y1(const __gmp_expr< T, U > &expr)
__gmp_expr< T, __gmp_unary_expr< __gmp_expr< T, U >, __gmp_exp_function > > exp(const __gmp_expr< T, U > &expr)
size_t blossom_maximum_cardinality_matching(const GT &g, DynDlist< typename GT::Arc * > &matching, SA sa=SA())
Alias of compute_maximum_cardinality_general_matching().
Main namespace for Aleph-w library functions.
uint64_t mod_inv(const uint64_t a, const uint64_t m)
Modular Inverse.
T ext_gcd(T a, T b, T &x, T &y) noexcept
Extended Euclidean Algorithm.
and
Check uniqueness with explicit hash + equality functors.
std::decay_t< typename HeadC::Item_Type > T
uint64_t mod_exp(uint64_t base, uint64_t exp, const uint64_t m)
Modular exponentiation.
uint64_t mod_mul(uint64_t a, uint64_t b, uint64_t m)
Safe 64-bit modular multiplication.
uint64_t crt(const Array< uint64_t > &rem, const Array< uint64_t > &mod)
Chinese Remainder Theorem (CRT).
double mod(double a, double b)
FooMap m(5, fst_unit_pair_hash, snd_unit_pair_hash)
Dynamic array container with automatic resizing.