做题记录1

BZOJ2005

首先我们将$2k+1$变换一下.显然有$2k+1=(2gcd{x,y})-1$这个事实.那么我们对$\gcd{x,y}$分区统计,方法参照http://www.contesthunter.org/record/43602我的SXBK题.

#include <cstdio>
int m,n,i,j,k;
long long fc[200000],ans;
int main(){
	scanf("%d%d",&n,&m);
	if(n>m){
		n^=m;
		m^=n;
		n^=m;
	}
	for(i=n;i;--i){
		fc[i]=((long long)(n/i))*(m/i);
		for(j=2*i;j<=m;++j) fc[i]-=fc[j];
		ans+=fc[i]*(2*i-1);
	}
	printf("%lld\n",ans);
	return 0;
}

SPOJ Visible Lattice Points

求给定$N$,$(x,y,z)=1,1\le x,y,z\le N$中$(x,y,z)$的对数.

我们考虑莫比乌斯反演.

http://quartergeek.com/eight-gcd-problems/ 讲得比较清楚.

#include <cstdio>
int pr[100000],pl,mu[2000000],i;
int prm[2000000],T,n;
int genMu(int n){
	int i,j,k;
	mu[1]=1;
	for(i=2;i<=n;++i){
		if(!prm[i]){
			mu[i]=-1;
			prm[i]=pr[pl++]=i;
		}
		for(j=0;j<pl&&(k=pr[j]*i)<=n;++j){
			prm[k]=pr[j];
			if(prm[i]==pr[j]){
				mu[k]=0;
				break;
			}else{
				mu[k]=-mu[i];
			}
		}
	}
}
long long ans;
inline long long cb(long long a){
	return a*a*a;
}
inline long long sq(long long a){
	return a*a;
}
int main(){
	genMu(1000000);
	scanf("%d",&T);
	while(T--){
		scanf("%d",&n);
		ans=3LL;
		for(i=1;i<=n;++i) ans+=((long long)(mu[i]))*cb((long long)(n/i));
		for(i=1;i<=n;++i) ans+=((long long)(mu[i]))*sq((long long)(n/i))*3LL;
		printf("%lld\n",ans);
	}
	return 0;
}

BZOJ 1101 (POI)

原文地址:https://www.cnblogs.com/tmzbot/p/4462992.html