首页 > 其他 > 详细

Square-free integers SPOJ - SQFREE

时间:2021-06-17 23:07:21      阅读:25      评论:0      收藏:0      [点我收藏+]

原题链接
考察:容斥原理 or 莫比乌斯反演
思路:
??枚举平方数:
\(2^2,3^2,4^2,5^2,6^2,...,1e^{7^2}\)
??对于\(2^2\)需要减去,\(3^2\)需要减去,\(4^2\)不需要计入,\(6^2\)需要减去...如果忽视指数,这就对应了莫比乌斯函数,我们预处理1e7以内的质数,然后利用\(mob[i]\times\frac{n}{i\times i}\)即可.注意到这里可以分块,但是求的右端点是需要sqrt的,因为我们是在平方数的下标下求和.

Code

#include <iostream>
#include <cstring>
#include <cmath>
using namespace std;
typedef long long LL;
const int N = 1e7+10;
int prime[N],cnt,mob[N],sum[N];
bool st[N];
LL n;
void GetPrime(int n) 
{
	mob[1] = 1;
	for(int i=2;i<=n;i++)
	{
		if(!st[i]) prime[++cnt] = i,mob[i] = -1;
		for(int j=1;prime[j]<=n/i;j++)
		{
			st[i*prime[j]] = 1;
			if(i%prime[j]==0) break;
			mob[i*prime[j]] = (-1)*mob[i];
		}
	}
	for(int i=1;i<=n;i++)
	  sum[i] = sum[i-1]+mob[i];
}
int main()
{
	int T;
	scanf("%d",&T);
	GetPrime(N-1);
	while(T--)
	{
		scanf("%lld",&n);
		LL ans = 0;
		for(LL i=1,r;i<=n/i;i=r+1)
		{
			r = sqrt(n/(n/(i*i)));
			ans+=(LL)(sum[r]-sum[i-1])*(n/(i*i));
		}
		printf("%lld\n",ans);
	}
	return 0;
}

Square-free integers SPOJ - SQFREE

原文:https://www.cnblogs.com/newblg/p/14897250.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!