Bzoj 2006
Bzoj 2819

Bzoj 2818

coc youyl posted @ 2015年6月19日 22:39 in bzoj , 557 阅读

题目链接:

题目分类:

题意:

给定整数n,求x和y都在1到n之间且gcd(x,y)为素数的数对有多少对。

题解:

可以考虑枚举gcd(x,y)的值,然后问题变成在一个范围内的互质的数对有多少对。

这个可以使用phi函数的前缀和完成。

程序:

#include<cstdio>
using namespace std;
bool isp[12000000];
int n;
int phi[12000000];
int mi[12000000];
long long f[12000000];
inline int min(int x,int y)
{
	if(x<y)return x;
	return y;
}
inline void shai()
{
	for (int i=1;i<=n;i++)mi[i]=100000000;
	for (int i=2;i<=n;i++)
	{
		if(isp[i]==0)
		{
			mi[i]=i;
			for (int j=i+i;j<=n;j+=i)
			{
				isp[j]=1;
				mi[j]=min(mi[j],i);
			}
		}
	}
}
inline void getphi()
{
	phi[1]=1;
	for (int i=2;i<=n;i++)
	{
		if((i/mi[i])%mi[i]==0)
		{
			phi[i]=phi[i/mi[i]]*mi[i];
		}
		else
		{
			phi[i]=phi[i/mi[i]]*(mi[i]-1);
		}
	}
	f[1]=1LL;
	for (int i=2;i<=n;i++)
	{
		f[i]=f[i-1]+((long long)phi[i])*2LL;
	}
}
inline long long getans()
{
//	for (int i=1;i<=n;i++)printf("%d ",phi[i]);
	long long ans=0;
	for (int i=2;i<=n;i++)
	{
		if(isp[i]==0)
		{
			ans+=(long long)f[n/i];
		}
	}return ans;
}
int main()
{
	scanf("%d",&n);
	shai();
	getphi();
	printf("%lld\n",getans());
	return 0;
}

登录 *


loading captcha image...
(输入验证码)
or Ctrl+Enter