CF1336D Yui and Mahjong Set

题目传送门

分析:
日常被开除人籍
通过顺子刻子数量的改变,准确找出每张牌的数量
直接膜拜大佬博客OrzOrz

#include<cstdio>
#include<cmath>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<queue>
#include<set>
#include<map>
#include<vector>
#include<string>

#define maxn 1000005
#define INF 0x3f3f3f3f

using namespace std;

inline int getint()
{
	int num=0,flag=1;char c;
	while((c=getchar())<'0'||c>'9')if(c=='-')flag=-1;
	while(c>='0'&&c<='9')num=num*10+c-48,c=getchar();
	return num*flag;
}

int n,cnt;
int T[maxn],S[maxn];
int ans[maxn];

inline void ask(int x)
{printf("+ %d\n",x),fflush(stdout),T[++cnt]=getint(),S[cnt]=getint();}

int main()
{
	n=getint();
	T[0]=getint(),S[0]=getint();
	for(int i=1;i<=n;i++)ans[i]=-1;
	for(int i=1;i<n;i++)ask(i);ask(1);
	for(int i=n;i;i--)T[i]=T[i]-T[i-1],S[i]=S[i]-S[i-1];
	ans[1]=T[n]-T[1];
	for(int i=2;i<n;i++)if(T[i])
	{
		ans[i]=0;
		while(ans[i]*(ans[i]-1)/2<T[i])ans[i]++;
	}
	if(ans[3]==-1)ans[3]=(S[2]>0);
	if(ans[2]==-1)ans[2]=S[n]/(ans[3]+1)-1;
	for(int i=3;i<=n-2;i++)if(ans[i+1]==-1)
	{
		S[i]-=(ans[i-1]+1)*(ans[i-2]+1);
		ans[i+1]=(S[i]>0);
	}
	ans[n]=(S[n-1]-(ans[n-2]+1)*(ans[n-3]+1))/(ans[n-2]+1);
	printf("!");
	for(int i=1;i<=n;i++)printf(" %d",ans[i]);
	puts("");
}

posted @ 2020-07-18 16:07  Izayoi_Doyo  阅读(171)  评论(0编辑  收藏  举报