欧拉函数小记
简单整理一下欧拉函数的相关内容、
定义
φ(n) 表示在[1,n]内,所有与n互质的数的个数。
通式:
$φ(n) = n\prod\limits_{i=1}^k (1-\frac{1}{p_i}) $
或者
$φ(n) = n\prod\limits_{i=1}^k (\frac{p_i-1}{p_i}) $
其中:
$n = p_1^{a_1}p_1^{a_2}...p_k^{a_k}$
其中φ(1) = 1
特别的,当n是素数时,φ(n) = n-1
性质
1、欧拉函数是积性函数,即
当(n,m)=1时,$φ(n*m) = φ(n) * φ(m)$
2、欧拉定理
$x^{φ(p)} ≡ 1 (mod m)$
3、特殊性质
若n是奇数
φ(2n) = φ(n)
求欧拉函数
1、通式求法
即按照定义中的通式求,复杂度$O(\sqrt{n})$
1 //为了防止小数,所以假设在开始时,已经没有了分母,即pi 2 //那么对于有些素因子有多个的,需要再乘上 3 //因为去分母只去了一个素因子,那么需要再乘ai-1个 4 int getphi(int x) { 5 int ret = 1; 6 for (int i=2; i*i<=x; ++i) { 7 if (x % i == 0) { 8 ret *= (i-1); 9 x /= i; 10 while (x % i == 0) x /= i, ret *= i; 11 } 12 } 13 if (x > 1) ret *= (x - 1); // x是素数 14 return ret; 15 }
2、线性筛法
使用线性筛素数的板子,稍加修改。分为三种情况
(1)若n是素数,根据定义,φ(n)=n-1;
(2)若n不是素数,设n=i*p,其中p是素数。此时再分为两种情况。
- 如果i%p==0,φ(i*p)=φ(i)*p
- 如果i%p!=0,φ(i*p)=φ(i)*(p-1)
网上很多大牛都有对于这一步的证明,而我自己乱搞了一下,一个比较直观的证明
对于第二条,很显然,由欧拉函数是积性函数可以推出。
第一条:i%p==0,那么将i质因数分解后,其中一定有p
那么,n(即i*p)质因数分解后的质因子与i分解后的相同,个数也相同。
然后在看一下定义,发现,现在φ(i)只要乘上一个p就是φ(n)了。
即:
$i=p_1^{a_1}p_2^{a_2}...p^a...p_k^{a_k}$
$n=p_1^{a_1}p_2^{a_2}...p^{a+1}...p_k^{a_k}$
$φ(i) = i*\frac{1}{1-p_1}\frac{1}{1-p_2}...\frac{1}{1-p}...\frac{1}{1-p_k}$
$φ(n) = i*p*\frac{1}{1-p_1}\frac{1}{1-p_2}...\frac{1}{1-p}...\frac{1}{1-p_k} = n*\frac{1}{1-p_1}\frac{1}{1-p_2}...\frac{1}{1-p}...\frac{1}{1-p_k}$
所以:φ(n)=φ(i)*p
1 void getphi() { 2 for (int i=2; i<=N; ++i) { 3 if (!noprime[i]) prime[++tot] = i,phi[i] = i-1; 4 for (int j=1; j<=tot&&i*prime[j]<=N; ++j) { 5 noprime[i * prime[j]] = true; 6 if (i % prime[j] == 0) {phi[i*prime[j]] = phi[i] * prime[j];break;} 7 phi[i * prime[j]] = phi[i] * (prime[j]-1); 8 } 9 } 10 }
例题