結果
問題 |
No.2120 場合の数の下8桁
|
ユーザー |
![]() |
提出日時 | 2025-03-20 20:27:29 |
言語 | PyPy3 (7.3.15) |
結果 |
AC
|
実行時間 | 122 ms / 2,000 ms |
コード長 | 2,687 bytes |
コンパイル時間 | 179 ms |
コンパイル使用メモリ | 82,380 KB |
実行使用メモリ | 74,868 KB |
最終ジャッジ日時 | 2025-03-20 20:28:56 |
合計ジャッジ時間 | 2,398 ms |
ジャッジサーバーID (参考情報) |
judge3 / judge2 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
other | AC * 20 |
ソースコード
import sys _cache_period_product = {} def get_period_product(p, e, pe): key = (p, e) if key in _cache_period_product: return _cache_period_product[key] product = 1 for i in range(1, pe): if i % p != 0: product = (product * i) % pe _cache_period_product[key] = product return product def factorial_mod_p(n, p, e): pe = p ** e if n == 0 or n == 1: return 1 period_product = get_period_product(p, e, pe) full_cycles = n // pe remainder = n % pe res = pow(period_product, full_cycles, pe) rem_product = 1 for i in range(1, remainder + 1): if i % p != 0: rem_product = (rem_product * i) % pe res = (res * rem_product) % pe recursive_part = factorial_mod_p(n // p, p, e) res = (res * recursive_part) % pe return res def factorial_exponent(n, p): count = 0 while n > 0: n = n // p count += n return count def comb_mod(M, N, p, e): if M < N or N < 0: return 0 if N == 0 or N == M: return 1 % (p ** e) v_p_M = factorial_exponent(M, p) v_p_N = factorial_exponent(N, p) v_p_MN = factorial_exponent(M - N, p) v_p_total = v_p_M - v_p_N - v_p_MN if v_p_total < 0: return 0 pe = p ** e if v_p_total >= e: return 0 numerator = factorial_mod_p(M, p, e) denominator_N = factorial_mod_p(N, p, e) denominator_MN = factorial_mod_p(M - N, p, e) denominator = (denominator_N * denominator_MN) % pe mod = p ** (e - v_p_total) try: inv_denominator = pow(denominator, -1, mod) except ValueError: return 0 part = (numerator * inv_denominator) % mod result = (part * pow(p, v_p_total, pe)) % pe return result def extended_gcd(a, b): if a == 0: return (b, 0, 1) else: g, y, x = extended_gcd(b % a, a) return (g, x - (b // a) * y, y) def chinese_remainder(remainders, moduli): res = 0 n = len(moduli) prod = 1 for m in moduli: prod *= m for i in range(n): p = prod // moduli[i] g, inv, _ = extended_gcd(p, moduli[i]) if g != 1: return None res = (res + remainders[i] * inv * p) % prod return res % prod def main(): M = int(sys.stdin.readline()) N = int(sys.stdin.readline()) if M < N: print("00000000") return mod1 = 256 mod2 = 5 ** 8 c1 = comb_mod(M, N, 2, 8) c2 = comb_mod(M, N, 5, 8) res = chinese_remainder([c1, c2], [mod1, mod2]) if res is None: print("00000000") else: print("{:08d}".format(res % 10**8)) if __name__ == "__main__": main()