备战CSP——Ling最近学的数学模板
- 质数的判定
inline bool isprime(int n)
{
if(n<2) return false;
for(int i=2;i<=sqrt(n);i++)
{
if(n%i==0) return false;
}
return true;
}
上面这个算法称之为“试除法”,可以以 O ( N ) O(\sqrt{N}) O(N)的复杂度求出一个数是否是质数。
- E r a t o s t h e n e s Eratosthenes Eratosthenes质数筛
bool prime[100005];
inline void shai_prime
{
memset(prime,1,sizeof(prime));//all prime
prime[1]=false;//'1' is not a prime
for(int i=2;i<=n;i++)//start from 2
{
if(!prime[i]) continue;
else
{
for(int j=1;j<=n/i;j++)
prime[i*j]==false;// tag it
}
}
}
上面的算法采用的“以空间换时间”的策略,复杂度为 O ( N l o g l o g N ) O(NloglogN) O(NloglogN),已经非常接近线性。
- 质因数分解
算数基本定理:任何一个大于1的正整数都可以唯一分解成若干个有限个质数的乘积,可写作:
N = p 1 c 1 p 2 c 2 . . . p m c m N=p^{c_1}_1p^{c_2}_2...p^{c_m}_m N=p1c1p2c2...pmcm
其中 c i ∈ N ∗ c_i \in \mathbb N^* ci∈N∗,且 p i p_i pi严格单调递减。
试除法:
int p[maxn],c[maxn];//store num & pow
inline void devide(int n)
{
int m=0;
for(int i=2;i<=sqrt(n);i++)
{
if(n%i==0)
{
p[++m]==i;
c[m]=0;
while(n%i==0)
{
n/=i;
c[m]++;
}
}
}
if(n>1)
{
p[++m]=n;
c[m]=1;
}
for(int i=1;i<=m;i++)
{
cout<<p[i]<<'^'<<c[i]<<endl;//print them
}
}
时间复杂度为 O ( n ) O(\sqrt{n}) O(n)
- 最大公约数
更相减损术:
∀ a , b ∈ N , a ≥ b ; g c d ( a , b ) = g c d ( b , a − b ) = g c d ( a , a − b ) \forall a,b\in\mathbb N,a\geq b; gcd(a,b)=gcd(b,a-b)=gcd(a,a-b) ∀a,b∈N,a≥b;gcd(a,b)=gcd(b,a−b)=gcd(a,a−b)
∀ a , b ∈ N , g c d ( 2 a , 2 b ) = 2 g c d ( a , b ) \forall a,b\in\mathbb N,gcd(2a,2b)=2gcd(a,b) ∀a,b∈N,gcd(2a,2b)=2gcd(a,b)
欧几里得算法:
∀ a , b ∈ N , b ≠ 0 , g c d ( a , b ) = g c d ( b , a m o d b ) \forall a,b\in\mathbb N,b \neq\ 0,gcd(a,b)=gcd(b,a\space mod \space b) ∀a,b∈N,b= 0,gcd(a,b)=gcd(b,a mod b)
代码如下:
inline int gcd(int a,int b)
{
return b ? gcd(b,a%b) : a;
}
- E u l e r Euler Euler 函数
1 − n 1-n 1−n中所有与 N N N互质的数的个数被称为欧拉函数,记为 φ ( n ) \varphi(n) φ(n).
若在算数基本定理中, N = Π i = 1 m p i c i N=\Pi^{m}_{i=1}p_i^{c_i} N=Πi=1mpici,则:
φ ( N ) = N ∗ Π 质 数 p ∣ n ( 1 − 1 p ) \varphi(N)=N*\Pi_{质数p|n}(1-\frac{1}{p}) φ(N)=N∗Π质数p∣n(1−p1)
求法(即试除法):
inline int phi(int n)
{
int ans=n;
for(int i=2;i<=sqrt(n);i++)
{
if(n%i==0)
{
ans=ans/i*(i-1);
while(n%i==0) n/=i;
}
}
if(n>1) ans=ans/n*(n-1);
return ans;
}
-
F e r m a t Fermat Fermat小定理
i f p r i m e [ p ] , ∀ a ∈ N , a p ≡ a ( m o d p ) if\space prime[p],\forall a\in\mathbb N,a^p\equiv a(mod\space p) if prime[p],∀a∈N,ap≡a(mod p) -
E u l e r Euler Euler定理
i f g c d ( a , b ) = 1 , t h e n a φ ( n ) ≡ 1 ( m o d n ) if\space gcd(a,b)=1,then \space a^{\varphi(n)}\equiv 1(mod \space n) if gcd(a,b)=1,then aφ(n)≡1(mod n) -
E u l e r Euler Euler定理推论
i f b > φ ( n ) , a b ≡ a b m o d φ ( n ) + φ ( n ) ( m o d n ) if \space b>\varphi(n),a^b\equiv a^{b \space mod\space \varphi(n)+\space \varphi(n)}(mod\space n) if b>φ(n),ab≡ab mod φ(n)+ φ(n)(mod n)
可用来对除法运算取模。 -
扩展欧几里得算法
主要是求解形如:
a x + b y = g c d ( a , b ) ax+by=gcd(a,b) ax+by=gcd(a,b)
的方程。代码如下:
inline void exgcd(int a,int b,int &x,int &y)
{
if(b==0)
{
x=1;y=1;return a;
}
else
{
int d=exgcd(b,a%b,x,y);
int z=x;x=y;y=z-y*(a/b);
return d;
}
}
计划:了解原理,集训时把板子打熟。