1.欧拉函数
给定 nn 个正整数 aiai,请你求出每个数的欧拉函数。
欧拉函数的定义
1∼N1∼N 中与 NN 互质的数的个数被称为欧拉函数,记为 ϕ(N)ϕ(N)。
若在算数基本定理中,N=pa11pa22…pammN=p1a1p2a2…pmam,则:
ϕ(N)ϕ(N) = N×p1−1p1×p2−1p2×…×pm−1pmN×p1−1p1×p2−1p2×…×pm−1pm
输入格式
第一行包含整数 nn。
接下来 nn 行,每行包含一个正整数 aiai。
输出格式
输出共 nn 行,每行输出一个正整数 aiai 的欧拉函数。
数据范围
1≤n≤1001≤n≤100,
1≤ai≤2×109
#include <bits/stdc++.h>
//先分解质因数,然后根据公式代入,时间复杂度为n*根号下a[i]
using namespace std;
int main()
{
int n;
scanf("%d",&n);
while(n--)
{
int x;
scanf("%d",&x);
int res=x;
for(int i=2;i<=x/i;i++)
{
if(x%i==0)
{
while(x%i==0)
{
x=x/i;
}res=(res/i)*(i-1);
}
}
if(x>1) res=(res/x)*(x-1);
printf("%d\n",res);
}
return 0;
}
2.筛法求欧拉函数
思路:在线性筛的同时将从1到n的欧拉函数求一遍。
#include <bits/stdc++.h>
using namespace std;
const int N=1000010;
int primes[N],cnt;
int oula[N];
bool st[N];
void getoula(int n)
{
oula[1]=1;
for(int i=2;i<=n;i++)
{
if(!st[i])
{
primes[cnt++]=i;
oula[i]=i-1;
}
for(int j=0;primes[j]<=n/i;j++)
{
int t=primes[j]*i;
st[t]=true;
if(i%primes[j]==0)
{
oula[t]=oula[i]*primes[j];
break;
}
oula[t]=oula[i]*(primes[j]-1);
}
}
}
int main()
{
int n;
cin>>n;
getoula(n);
long long int res=0;
for(int i=1;i<=n;i++)
res+=oula[i];
cout<<res<<endl;
return 0;
}