// 求欧拉函数值 inteuler_phi(int n){ int m = int(sqrt(n + 0.5)); int ans = n; for(int i = 2;i <= m;i++) { if(0 == n % i) { ans = ans / i * (i - 1); while(0 == n % i) n /= i; } } if(n > 1) ans = ans / n * (n - 1); return ans; }
//欧拉函数 voideuler_init(int n){ phi[1] = 1; //pri[0] = pri[1] = 0; int cnt = 0; for (int i = 2; i <= n; ++i) { if (!vis[i]) { phi[i] = i - 1; pri[cnt++] = i; } for (int j = 0; j < cnt; ++j) { if (1ll * i * pri[j] >= n) break; vis[i * pri[j]] = 1; if (i % pri[j]) { phi[i * pri[j]] = phi[i] * (pri[j] - 1); // prr[j] 是素数 phi[j] = pri[j] - 1 } else { // i % pri[j] == 0 // 换言之,i 之前被 pri[j] 筛过了 // 由于 pri 里面质数是从小到大的,所以 i 乘上其他的质数的结果一定也是 // pri[j] 的倍数 它们都被筛过了,就不需要再筛了,所以这里直接 break // 掉就好了 phi[i * pri[j]] = phi[i] * pri[j]; break; } } } }
// 求欧拉函数值 inteuler_phi(int n){ int m = int(sqrt(n + 0.5)); int ans = n; for(int i = 2;i <= m;i++) { if(0 == n % i) { ans = ans / i * (i - 1); while(0 == n % i) n /= i; } } if(n > 1) ans = ans / n * (n - 1); return ans; }