版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/Game_Acm/article/details/82054640
LL Abs( LL a ){ return a<0?-a:a; }
LL Min( LL a , LL b ){ return a<b?a:b; }
LL Max( LL a , LL b ){ return a>b?a:b; }
LL Gcd( LL a , LL b ){ return b==0?a:Gcd( b , a%b ); }
LL arr[5] = { 2,3,5,233,331 };
LL Qmul( LL a , LL b , LL mod )
{
LL res = 0;
while ( b )
{
if ( b&1 )
res = ( res+a )%mod;
a = ( a+a )%mod;
b = b>>1;
}
return res;
}
LL Qpow( LL a , LL b , LL mod )
{
LL res = 1;
while ( b )
{
if ( b&1 )
res = Qmul( res , a , mod );
a = Qmul( a , a , mod );
b = b>>1;
}
return res;
}
bool Miller_Rabin( LL n )
{
if ( n==2 ) return true;
if ( n <2||n%2==0 ) return false;
LL m = n-1,k = 0;
while ( m%2==0 ) k++,m>>=1;
for ( int i=0 ; i<5 ; i++ )
{
LL a = arr[i]%(n-1)+1;
LL x = Qpow( a , m , n );
for ( int j=1 ; j<=k ; j++ )
{
LL y = Qmul( x , x , n );
if ( y==1&&x!=1&&x!=n-1 )
return false;
x = y;
}
if ( x!=1 ) return false;
}
return true;
}
LL fac[110],tol;
LL Pollard_rho( LL x , LL c )
{
LL i=1,k=2;
LL x0 = rand()%x;
LL y0 = x0;
while ( 1 )
{
i++;
x0 = ( Qmul( x0 , x0 , x )+c )%x;
LL d0 = Gcd( Abs( y0-x0 ) , x );
if ( d0!=1&&d0!=x ) return d0;
if ( y0==x0 ) return x;
if ( i == k ) { y0=x0; k+=k; }
}
}
void Findfac( LL n )
{
if ( Miller_Rabin( n ) )
{
fac[tol++] = n;
return;
}
LL p = n;
while ( p>=n )
p = Pollard_rho( p , rand()%(n-1)+1 );
Findfac( p );
Findfac( n/p );
}