Нужен быстрый алгоритм
Я бы хотел сравнить различные тесты простоты на скорость. Я хочу реализовать тест по теореме Вильсона. Мне нужно реализовать вычисление (p - 1)! mod p Но на мое удивление различные алгоритмы, хорошо себя показывающие при вычислении факториала, оказываются бесполезны, они проигрывают классическому вычислению через n! mod p = (n * (n - 1)!) mod p. Подскажите эффективные алгоритмы вычисления n! по простому модулю p>n, либо для данного частного случая. Я для вычисления n! без модуля использую алгоритм PrimeSwing, обгоняющий даже math.factorial, но я не думал над его версией для вычислений по модулю.
def factpow1(n, k):
res = 0
while n:
n = n // k
res += n % 2
return res
def SwingingFactorial(n):
t = 1
for i in primes(n):
t = (t * i ** factpow1(n, i))
return t
def PrimeSwing(n):
if n < 500:
return factorial(n)
else:
return SwingingFactorial(n) * PrimeSwing(n // 2) ** 2