题目链接:哆啦A梦传送门
题意:有长度为n的字符串,每个字符为'0'或'1',两个人轮流玩游戏,每次可以任取长度为k的连续子串,将它们改成相同的串(要么为1,要么为0),谁先把串弄成全部相同,谁就win。问:先手win,还是后手win。
题解:还是跟之前玩的博弈类似,两人都是最聪明的,那么也就是说,字符串一旦给定,其实已经定好了是先手win,还是后手win。
先手如果不能在第一次出手就win,那么之后它就不可能有win的概率,最多平局(后手也跟着先手取)。
那么即是先手第一次不能win时,他就要想方设法弄成平局。
先手第一次能win的条件:只需翻转k个就能使得整个串相同。
后手第一次能win的条件:
1,2*k>=n。
2,k!=1,k要为1,那么先手会原封不动的给后手。
3,判断长度为k的子串左右两边的两串是否相同。
当先手不能一次win时,他不会给后手好的条件,它要尽量使得后手再任意长度为k的子串左右两边的两串不满足情况。而且先手不会取首尾,他只会去中间连续子串。
#include<cstdio>
#include<algorithm>
#include<cstring>
using namespace std;
char op[100010];
int a[100010];
int sum[100010];
int n,m;
/*
5 1
11111
*/
int q_sum(int l,int r)
{
if(l>r) return 0;
return sum[r]-sum[l-1];
}
bool fir() ///判断先手能否第一次就win
{
for(int i=1;i<=n-m+1;i++)
{
int item=q_sum(1,i-1)+q_sum(i+m,n);
if(item==0||item+m==n) return 1;
}
return 0;
}
bool sec()
{
///后手
if(m==1||2*m<n) return 0;
int len=n-m-1;
///这里的意思其实就是前m-1个字符要统一,后m-1个字符要统一,且左右两串字符不同
///那么先手不管怎么取,后手总能win
for(int i=2;i<=len;i++)
{
if(a[i]!=a[i-1]||a[n-i+1]!=a[n-i+2]) return 0;
}
if(a[1]==a[n]) return 0;
return 1;
}
int main()
{
scanf("%d%d",&n,&m);
scanf("%s",op);
for(int i=1;i<=n;i++)
{
a[i]=op[i-1]-'0';
sum[i]=sum[i-1]+a[i];
}
if(fir()){
puts("tokitsukaze");
}
else{
if(sec()){
puts("quailty");
}
else{
puts("once again");
}
}
return 0;
}