AtCoder Beginner Contest 162 solution

感觉降智了,比赛时最后两题没写出来

真的是普及难度,我下次一定要AK and 涨Rating(咕咕咕)

A A

int n; qr(n);
while(n) {
    if(n%10==7) {puts("Yes");return 0;}
    n/=10;
}puts("No");

B B

简单容斥/ f o r   f o r   f o r for ~for~ for

ll n,ans;

ll f(ll x) {
	return (x+1)*x>>1;
}

int main() {
	qr(n); 
	ans=f(n)+15*f(n/15)-3*f(n/3)-5*f(n/5);
	pr2(ans);
	return 0;
}
ll n,ans;

int main() {
    qr(n);
    for(int i=1;i<=n;i++)
        ans+=(i%3!=0&&i%5!=0)*i;
   	pr2(ans);
}

我为啥要打容斥原理呢,人类迷惑行为

C C

莫比乌斯反演

ll ans,n;

int gcd(int x,int y) {return !x?y:gcd(y%x,x);}

int main() {
	qr(n); 
	for(int i=1;i<=n;i++)
		for(int j=1;j<=n;j++) {
			int k=gcd(i,j);
			for(int l=1;l<=n;l++)
				ans+=gcd(k,l);
		}
	pr2(ans);
	return 0;
}

其实开个桶可以实现 O ( n 2 ) O(n^2) ,但是何必呢?

D D

int n,sum[5][N],ys[150];
ll ans;
char s[N];

int main() {
	qr(n); scanf("%s",s+1);
	ys['R']=1;ys['G']=2; ys['B']=3;
	for(int i=1;i<=n;i++) {
		sum[1][i]=sum[1][i-1];
		sum[2][i]=sum[2][i-1];
		sum[3][i]=sum[3][i-1];
		sum[ys[s[i]]][i]++;
	}
	for(int i=1;i<n;i++)
		for(int j=i+1,k;j<n;j++) if(s[i]^s[j]) {
			k=j*2-i;
			ans+=sum[6-ys[s[i]]-ys[s[j]]][n]-
				 sum[6-ys[s[i]]-ys[s[j]]][j]-
				 (ys[s[k]]==6-ys[s[i]]-ys[s[j]]);
		}
	pr2(ans);
	return 0;
}

E E

简单容斥,比赛时没想到.

int n,m,f[N]; ll ans;
void upd(int &x) {x+=x>>31&mod;}
ll power(ll a,ll b=n) {
	ll c=1;
	while(b&&a>1) {
		if(b&1) c=c*a%mod;
		b=b/2;  a=a*a%mod;
	}
	return c;
}

int main() {
	qr(n); qr(m);
	for(int i=m; i;i--) {
		f[i]=power(m/i,n);
		for(int j=i*2;j<=m;j+=i) upd(f[i]-=f[j]);
		ans+=(ll)f[i]*i%mod;
	}
	pr2(ans%mod);return 0;
}

F F

f [ i ] f[i] 表示 i i 个数中选择 i / 2 \lfloor i/2\rfloor 个的最大和.

int n,a[N];
ll f[N],s[N];

int main() {
	scanf("%d",&n);
	for(int i=1;i<=n;i++) {
		scanf("%d",&a[i]);
		s[i]=(i>1?s[i-2]:0)+a[i];
	}
	for(int i=2;i<=n;i++)
		if(i&1) f[i]=max(f[i-1],f[i-2]+a[i]);
		else f[i]=max(s[i-1],f[i-2]+a[i]);
	printf("%lld\n",f[n]);return 0;
}

猜你喜欢

转载自blog.csdn.net/qq_42886072/article/details/105478471