欧拉函数线性筛法

首先我们知道欧拉函数是1到n-1中与n互质的数的个数。

除此之外,我们还要知道一些性质:

当p是素数时

1.   phi(p)=p-1。(不多bb)

2.   phi(p^k)=(p-1)*p^(k-1)

证明:

令n == p^k,小于 n 的正整数共有 p^k-1 个,其中与 p 不互素的个数共 p^(k-1)-1 个,它们是 1*p,2*p,3*p ... (p^(k-1)-1)*p

所以phi(p^k) == (p^k-1) - (p^(k-1)-1) == p^k - p^(k-1) == (p-1) * p^(k-1)。

3.   如果i%p==0,那么phi(i*p)=p*phi(i);(自行理解)

4.   如果i%p!=0,那么phi(i*p)=(p-1)*phi(i);

证明:

因为欧拉函数是积性函数,所以有phi(i*p)=phi(i)*phi(p),然后p是素数,所以phi(i*p)=(p-1)*phi(i);

知道了上面的四个性质,相信大家就可以写出线性筛法求欧拉函数的代码了.

我用的是欧拉筛法的同时筛出欧拉数(啦啦啦):

int prime[1000045],cnt;

int phi[1000045];

bool vis[1000045];

il void shai()
{
	for(int i=2;i<=1000045;i++)
		{
			if(!vis[i])//su shu
				{
					prime[++cnt]=i;
					phi[i]=i-1;//xing zhi 1
				}
			for(int j=1;j<=cnt;j++)
				{
					if(i*prime[j]>100000)
						break;
					vis[i*prime[j]]=1;
					if(i%prime[j]==0)
						{
							phi[i*prime[j]]=prime[j]*phi[i];//xing zhi 3
							break;
						}
					else
						phi[i*prime[j]]=(prime[j]-1)*phi[i];//xing zhi 4
				}
		}
}
原文地址:https://www.cnblogs.com/gshdyjz/p/7678361.html