/*3.欧拉函数
对正整数n,欧拉函数是少于或等于n的数中与n互质的数的数目
显然对素数n,phi(n)=n-1
通式:φ(x)=x(1-1/p1)(1-1/p2)(1-1/p3)(1-1/p4)…..(1-1/pn),其中p1, p2……pn为x的所有质因数,x是不为0的整数。φ(1)=1(唯一和1互质的数就是1本身)
很简单,就不写代码什么的了
*/
降幂公式
当x≥ϕ(p)时,有ax≡axmodϕ(p)+ϕ(p)(mod p)
这部分可以参考“上帝与集合”
void init()
{
for(int i = 1; i < maxn; i++)
phi[i] = i;
for(int i = 2; i < maxn; i++) {
if(phi[i] == i) {
for(int j = i; j < maxn; j += i) {
phi[j] -= (phi[j] / i);
}
}
}
}
//直接求解欧拉函数
//根号n求欧拉函数 注意是 i*i<=x
LL euler(LL n)
{
//返回euler(n)
LL res = n, a = n;
for(LL i = 2; i * i <= a; i++) {
if(a % i == 0) {
res = res / i * (i - 1); //先进行除法是为了防止中间数据的溢出
while(a % i == 0) a /= i;
}
}
if(a > 1) res = res / a * (a - 1);
return res;
}
//O(n)求欧拉函数
int prime[N + 5], phi[N + 5]; bool noprime[N + 5];
//1. phi(p)=p-1 因为质数p除了1以外的因数只有p,故1至p的整数只有p与p不互质
//2. 如果i mod p = 0, 那么phi(i * p)=p * phi(i)
//3.若i mod p ≠0, 那么phi(i * p)=phi(i) * (p-1)
void euler(){
int size = 0;
phi[1] = 1;
for(int i = 2; i <= N; i++) {
if(!noprime[i]) {
prime[++size] = i;
phi[i] = i - 1;
}
for(int j = 1; j <= size && i * prime[j] <= N - 5; j++) {
noprime[i * prime[j]] = 1;
if(i % prime[j] == 0) {
phi[i * prime[j]] = prime[j] * phi[i]; //!!
break;
}
phi[i * prime[j]] = phi[i] * (prime[j] - 1);
}
}
}
求欧拉函数
猜你喜欢
转载自blog.csdn.net/qq_39599067/article/details/81170021
今日推荐
周排行