Compute n! under modulo p
Last Updated :
31 Jul, 2022
Given a large number n and a prime p, how to efficiently compute n! % p?
Examples :
Input: n = 5, p = 13
Output: 3
5! = 120 and 120 % 13 = 3
Input: n = 6, p = 11
Output: 5
6! = 720 and 720 % 11 = 5
A Naive Solution is to first compute n!, then compute n! % p. This solution works fine when the value of n! is small. The value of n! % p is generally needed for large values of n when n! cannot fit in a variable, and causes overflow. So computing n! and then using modular operator is not a good idea as there will be overflow even for slightly larger values of n and r.
Following are different methods.
Method 1 (Simple)
A Simple Solution is to one by one multiply result with i under modulo p. So the value of result doesn’t go beyond p before next iteration.
C++
#include <bits/stdc++.h>
using namespace std;
int modFact( int n, int p)
{
if (n >= p)
return 0;
int result = 1;
for ( int i = 1; i <= n; i++)
result = (result * i) % p;
return result;
}
int main()
{
int n = 25, p = 29;
cout << modFact(n, p);
return 0;
}
|
Java
import java.io.*;
class GFG
{
static int modFact( int n,
int p)
{
if (n >= p)
return 0 ;
int result = 1 ;
for ( int i = 1 ; i <= n; i++)
result = (result * i) % p;
return result;
}
public static void main (String[] args)
{
int n = 25 , p = 29 ;
System.out.print(modFact(n, p));
}
}
|
Python3
def modFact(n, p):
if n > = p:
return 0
result = 1
for i in range ( 1 , n + 1 ):
result = (result * i) % p
return result
n = 25 ; p = 29
print (modFact(n, p))
|
C#
using System;
class GFG {
static int modFact( int n, int p)
{
if (n >= p)
return 0;
int result = 1;
for ( int i = 1; i <= n; i++)
result = (result * i) % p;
return result;
}
static void Main()
{
int n = 25, p = 29;
Console.Write(modFact(n, p));
}
}
|
PHP
<?php
function modFact( $n , $p )
{
if ( $n >= $p )
return 0;
$result = 1;
for ( $i = 1; $i <= $n ; $i ++)
$result = ( $result * $i ) % $p ;
return $result ;
}
$n = 25; $p = 29;
echo modFact( $n , $p );
?>
|
Javascript
<script>
function modFact(n,p)
{
if (n >= p)
return 0;
let result = 1;
for (let i = 1; i <= n; i++)
result = (result * i) % p;
return result;
}
let n = 25, p = 29;
document.write(modFact(n, p));
</script>
|
Output :
5
Time Complexity : O(n).
Auxiliary Space : O(1) since using only constant space
Method 2 (Using Sieve)
The idea is based on below formula discussed here.
The largest possible power of a prime pi that divides n is,
?n/pi? + ?n/(pi2)? + ?n/(pi3)? + .....+ 0
Every integer can be written as multiplication of powers of primes. So,
n! = p1k1 * p2k2 * p3k3 * ....
Where p1, p2, p3, .. are primes and
k1, k2, k3, .. are integers greater than or equal to 1.
The idea is to find all primes smaller than n using Sieve of Eratosthenes. For every prime ‘pi‘, find the largest power of it that divides n!. Let the largest power be ki. Compute piki % p using modular exponentiation. Multiply this with final result under modulo p.
Below is implementation of above idea.
C++
#include <bits/stdc++.h>
using namespace std;
int largestPower( int n, int p)
{
int x = 0;
while (n) {
n /= p;
x += n;
}
return x;
}
int power( int x, int y, int p)
{
int res = 1;
x = x % p;
while (y > 0) {
if (y & 1)
res = (res * x) % p;
y = y >> 1;
x = (x * x) % p;
}
return res;
}
int modFact( int n, int p)
{
if (n >= p)
return 0;
int res = 1;
bool isPrime[n + 1];
memset (isPrime, 1, sizeof (isPrime));
for ( int i = 2; i * i <= n; i++) {
if (isPrime[i]) {
for ( int j = 2 * i; j <= n; j += i)
isPrime[j] = 0;
}
}
for ( int i = 2; i <= n; i++) {
if (isPrime[i]) {
int k = largestPower(n, i);
res = (res * power(i, k, p)) % p;
}
}
return res;
}
int main()
{
int n = 25, p = 29;
cout << modFact(n, p);
return 0;
}
|
Java
import java.util.Arrays;
public class GFG {
static int largestPower( int n, int p) {
int x = 0 ;
while (n > 0 ) {
n /= p;
x += n;
}
return x;
}
static int power( int x, int y, int p) {
int res = 1 ;
x = x % p;
while (y > 0 ) {
if (y % 2 == 1 ) {
res = (res * x) % p;
}
y = y >> 1 ;
x = (x * x) % p;
}
return res;
}
static int modFact( int n, int p) {
if (n >= p) {
return 0 ;
}
int res = 1 ;
boolean isPrime[] = new boolean [n + 1 ];
Arrays.fill(isPrime, true );
for ( int i = 2 ; i * i <= n; i++) {
if (isPrime[i]) {
for ( int j = 2 * i; j <= n; j += i) {
isPrime[j] = false ;
}
}
}
for ( int i = 2 ; i <= n; i++) {
if (isPrime[i]) {
int k = largestPower(n, i);
res = (res * power(i, k, p)) % p;
}
}
return res;
}
static public void main(String[] args) {
int n = 25 , p = 29 ;
System.out.println(modFact(n, p));
}
}
|
Python3
def largestPower(n, p):
x = 0
while (n):
n / / = p
x + = n
return x
def power( x, y, p):
res = 1
x = x % p
while (y > 0 ) :
if (y & 1 ) :
res = (res * x) % p
y = y >> 1
x = (x * x) % p
return res
def modFact( n, p) :
if (n > = p) :
return 0
res = 1
isPrime = [ 1 ] * (n + 1 )
i = 2
while (i * i < = n):
if (isPrime[i]):
for j in range ( 2 * i, n, i) :
isPrime[j] = 0
i + = 1
for i in range ( 2 , n):
if (isPrime[i]) :
k = largestPower(n, i)
res = (res * power(i, k, p)) % p
return res
if __name__ = = "__main__" :
n = 25
p = 29
print (modFact(n, p))
|
C#
using System;
public class GFG {
static int largestPower( int n, int p) {
int x = 0;
while (n > 0) {
n /= p;
x += n;
}
return x;
}
static int power( int x, int y, int p) {
int res = 1;
x = x % p;
while (y > 0) {
if (y % 2 == 1) {
res = (res * x) % p;
}
y = y >> 1;
x = (x * x) % p;
}
return res;
}
static int modFact( int n, int p) {
if (n >= p) {
return 0;
}
int res = 1;
bool []isPrime = new bool [n + 1];
for ( int i = 0;i<n+1;i++)
isPrime[i] = true ;
for ( int i = 2; i * i <= n; i++) {
if (isPrime[i]) {
for ( int j = 2 * i; j <= n; j += i) {
isPrime[j] = false ;
}
}
}
for ( int i = 2; i <= n; i++) {
if (isPrime[i]) {
int k = largestPower(n, i);
res = (res * power(i, k, p)) % p;
}
}
return res;
}
static public void Main() {
int n = 25, p = 29;
Console.WriteLine(modFact(n, p));
}
}
|
PHP
<?php
function largestPower( $n , $p )
{
$x = 0;
while ( $n )
{
$n = (int)( $n / $p );
$x += $n ;
}
return $x ;
}
function power( $x , $y , $p )
{
$res = 1;
$x = $x % $p ;
while ( $y > 0)
{
if ( $y & 1)
$res = ( $res * $x ) % $p ;
$y = $y >> 1;
$x = ( $x * $x ) % $p ;
}
return $res ;
}
function modFact( $n , $p )
{
if ( $n >= $p )
return 0;
$res = 1;
$isPrime = array_fill (0, $n + 1, true);
for ( $i = 2; $i * $i <= $n ; $i ++)
{
if ( $isPrime [ $i ])
{
for ( $j = 2 * $i ; $j <= $n ; $j += $i )
$isPrime [ $j ] = 0;
}
}
for ( $i = 2; $i <= $n ; $i ++)
{
if ( $isPrime [ $i ])
{
$k = largestPower( $n , $i );
$res = ( $res * power( $i , $k , $p )) % $p ;
}
}
return $res ;
}
$n = 25;
$p = 29;
echo modFact( $n , $p );
?>
|
Javascript
<script>
function largestPower(n, p)
{
let x = 0;
while (n > 0) {
n = parseInt(n / p, 10);
x += n;
}
return x;
}
function power(x, y, p)
{
let res = 1;
x = x % p;
while (y > 0) {
if (y % 2 == 1) {
res = (res * x) % p;
}
y = y >> 1;
x = (x * x) % p;
}
return res;
}
function modFact(n, p) {
if (n >= p) {
return 0;
}
let res = 1;
let isPrime = new Array(n + 1);
for (let i = 0;i<n+1;i++)
isPrime[i] = true ;
for (let i = 2; i * i <= n; i++) {
if (isPrime[i]) {
for (let j = 2 * i; j <= n; j += i)
{
isPrime[j] = false ;
}
}
}
for (let i = 2; i <= n; i++) {
if (isPrime[i]) {
let k = largestPower(n, i);
res = (res * power(i, k, p)) % p;
}
}
return res;
}
let n = 25, p = 29;
document.write(modFact(n, p));
</script>
|
Output:
5
Time Complexity: O(nlog(logn))
Auxiliary Space: O(n)
This is an interesting method, but time complexity of this is more than Simple Method as time complexity of Sieve itself is O(n log log n). This method can be useful if we have list of prime numbers smaller than or equal to n available to us.
Method 3 (Using Wilson’s Theorem)
Wilson’s theorem states that a natural number p > 1 is a prime number if and only if
(p - 1) ! ? -1 mod p
OR (p - 1) ! ? (p-1) mod p
Note that n! % p is 0 if n >= p. This method is mainly useful when p is close to input number n. For example (25! % 29). From Wilson’s theorem, we know that 28! is -1. So we basically need to find [ (-1) * inverse(28, 29) * inverse(27, 29) * inverse(26) ] % 29. The inverse function inverse(x, p) returns inverse of x under modulo p (See this for details).
C++
#include <bits/stdc++.h>
using namespace std;
int power( int x, unsigned int y, int p)
{
int res = 1;
x = x % p;
while (y > 0) {
if (y & 1)
res = (res * x) % p;
y = y >> 1;
x = (x * x) % p;
}
return res;
}
int modInverse( int a, int p)
{
return power(a, p - 2, p);
}
int modFact( int n, int p)
{
if (p <= n)
return 0;
int res = (p - 1);
for ( int i = n + 1; i < p; i++)
res = (res * modInverse(i, p)) % p;
return res;
}
int main()
{
int n = 25, p = 29;
cout << modFact(n, p);
return 0;
}
|
Java
class GFG
{
static int power( int x, int y, int p)
{
int res = 1 ;
x = x % p;
while (y > 0 )
{
if ((y & 1 ) > 0 )
res = (res * x) % p;
y = y >> 1 ;
x = (x * x) % p;
}
return res;
}
static int modInverse( int a, int p)
{
return power(a, p - 2 , p);
}
static int modFact( int n, int p)
{
if (p <= n)
return 0 ;
int res = (p - 1 );
for ( int i = n + 1 ; i < p; i++)
res = (res * modInverse(i, p)) % p;
return res;
}
public static void main(String[] args)
{
int n = 25 , p = 29 ;
System.out.println(modFact(n, p));
}
}
|
Python3
def gcdExtended(a,b):
if (b = = 0 ):
return a, 1 , 0
g,x1,y1 = gcdExtended(b,a % b)
x1,y1 = y1,x1 - (a / / b) * y1
return g,x1,y1
for _ in range ( int ( input ())):
n,m = map ( int , input ().split())
if (n> = m):
print ( 0 )
else :
s = 1
for i in range (n + 1 ,m):
s = (s * i) % m
g,a,b = gcdExtended(s,m)
a = a % m
print (((m - 1 ) * a) % m)
|
C#
using System;
class GFG
{
public int power( int x, int y, int p)
{
int res = 1;
x = x % p;
while (y > 0)
{
if ((y & 1) > 0)
res = (res * x) % p;
y = y >> 1;
x = (x * x) % p;
}
return res;
}
public int modInverse( int a, int p)
{
return power(a, p - 2, p);
}
public int modFact( int n, int p)
{
if (p <= n)
return 0;
int res = (p - 1);
for ( int i = n + 1; i < p; i++)
res = (res * modInverse(i, p)) % p;
return res;
}
public static void Main()
{
GFG g = new GFG();
int n = 25, p = 29;
Console.WriteLine(g.modFact(n, p));
}
}
|
PHP
<?php
function power( $x , $y , $p )
{
$res = 1;
$x = $x % $p ;
while ( $y > 0)
{
if ( $y & 1)
$res = ( $res * $x ) % $p ;
$y = $y >> 1;
$x = ( $x * $x ) % $p ;
}
return $res ;
}
function modInverse( $a , $p )
{
return power( $a , $p - 2, $p );
}
function modFact( $n , $p )
{
if ( $p <= $n )
return 0;
$res = ( $p - 1);
for ( $i = $n + 1; $i < $p ; $i ++)
$res = ( $res *
modInverse( $i , $p )) % $p ;
return $res ;
}
$n = 25; $p = 29;
echo modFact( $n , $p );
?>
|
Javascript
<script>
function power(x, y, p)
{
let res = 1;
x = x % p;
while (y > 0)
{
if ((y & 1) > 0)
res = (res * x) % p;
y = y >> 1;
x = (x * x) % p;
}
return res;
}
function modInverse(a, p)
{
return power(a, p - 2, p);
}
function modFact(n, p)
{
if (p <= n)
return 0;
let res = (p - 1);
for (let i = n + 1; i < p; i++)
res = (res * modInverse(i, p)) % p;
return res;
}
let n = 25, p = 29;
document.write(modFact(n, p));
</script>
|
Output:
5
Time complexity of this method is O((p-n)*Logn)
Auxiliary Space : O(1) because using only constant variables
Method 4 (Using Primality Test Algorithm)
1) Initialize: result = 1
2) While n is not prime
result = (result * n) % p
3) result = (result * (n-1)) % p // Using Wilson's Theorem
4) Return result.
Note that time complexity step 2 of above algorithm depends on the primality test algorithm being used and value of the largest prime smaller than n. The AKS algorithm for example takes O(Log 10.5 n) time.
Share your thoughts in the comments
Please Login to comment...