Codeforces 1191E(Codeforces Round #573 (Div. 2) E)Tokitsukaze and Duel (博弈论)

2 篇文章 0 订阅
1 篇文章 0 订阅

题面

"Duel!"

Betting on the lovely princess Claris, the duel between Tokitsukaze and Quailty has started.

There are nn cards in a row. Each card has two sides, one of which has color. At first, some of these cards are with color sides facing up and others are with color sides facing down. Then they take turns flipping cards, in which Tokitsukaze moves first. In each move, one should choose exactly kk consecutive cards and flip them to the same side, which means to make their color sides all face up or all face down. If all the color sides of these nn cards face the same direction after one's move, the one who takes this move will win.

Princess Claris wants to know who will win the game if Tokitsukaze and Quailty are so clever that they won't make mistakes.

Input

The first line contains two integers nn and kk (1≤k≤n≤1051≤k≤n≤105).

The second line contains a single string of length nn that only consists of 00 and 11, representing the situation of these nn cards, where the color side of the ii-th card faces up if the ii-th character is 11, or otherwise, it faces down and the ii-th character is 00.

Output

Print "once again" (without quotes) if the total number of their moves can exceed 109109, which is considered a draw.

In other cases, print "tokitsukaze" (without quotes) if Tokitsukaze will win, or "quailty" (without quotes) if Quailty will win.

Note that the output characters are case-sensitive, and any wrong spelling would be rejected.

Examples

Input

4 2
0101

Output

quailty

Input

6 1
010101

Output

once again

Input

6 5
010101

Output

tokitsukaze

Input

4 1
0011

Output

once again

Note

In the first example, no matter how Tokitsukaze moves, there would be three cards with color sides facing the same direction after her move, and Quailty can flip the last card to this direction and win.

In the second example, no matter how Tokitsukaze moves, Quailty can choose the same card and flip back to the initial situation, which can allow the game to end in a draw.

In the third example, Tokitsukaze can win by flipping the leftmost five cards up or flipping the rightmost five cards down.

The fourth example can be explained in the same way as the second example does.

题目链接

Codeforces Round #573 (Div. 2) E || CF 1191E

题意

Tokitsukaze和Quailty决斗。

有一堆有正反两面的牌,以0101010111……形式排列(1为有色面朝上,0为有色面朝下)

回合制,每人每次可以使连续的k张牌朝上或朝下(朝同一个方向)

若本次操作后,所有牌朝朝同一个方向,则此次操作的玩家胜利。

Tokitsukaze先手

分析

有三种情况:

①若Tokitsukaze要胜利,则必须在Tokitsukaze第一次翻牌时胜利,不能给Quailty机会,使得Quailty能把他翻过去的牌翻回来。

即根据前缀和判断,能否用k一次将不同朝向牌翻过来。

即翻[left,left+k-1]牌时,左侧区间[0,left-1]和右侧[left+k,n-1]的牌全部同色,有一个left存在,Tokitsukaze就可以胜利

 

②若Quailty要胜利,则必须在Quailty第一次翻牌时胜利,不能给能给Tokitsukaze机会,使得Tokitsukaze能把他翻过去的牌翻回来。若Quailty在第一次翻牌时胜利,则无论之前Tokitsukaze怎么翻牌,Quailty都能胜利。

即当之前Tokitsukaze翻[left,left+k-1]牌时,Quailty能使左侧区间[0,left-1]和右侧[left+k,n-1]全部与中间[left,left+k-1]同色。

但两侧都有区间时,Quailty只能翻其中一个,且翻的区间长度<=k。则n>2*k时,Quailty赢不了。

则,则当[left,left+k-1]为0时,左右两侧至少有一侧为0,当[left,left+k-1]为1时,左右两侧至少有一侧为1。

则左右两侧,一侧为0,另一侧为1。对于所有的left,都能胜利,Quailty才能胜利。

当k==1时,假如Tokitsukaze不能在Tokitsukaze第一次翻牌时胜利。则Tokitsukaze可以将一张0的牌翻成0,或者一张1的牌翻成1(使朝同一个方向,不是0变1,1变0)则将牌原封不动地转给了Quailty。因为Tokitsukaze不能第一次翻牌时胜利,所以对于同样的牌,Quailty也不能第一次翻牌时胜利。所以k==1时,Quailty不能胜利。

 

③双方都不能在自己第一次翻牌时胜利,则进入扯皮环节,回合次数无限。

程序

#include<stdio.h>

#define maxn 100005
struct Node
{
    int item;
    int num_0,num_1;
}node[maxn];
char s[maxn];
int n,k;
bool judge_first()
{
    if(k>=n)
        return true;
    for(int left=0;left+k-1<=n-1;left++)
    {
        bool flag=true;
        if(left!=0)
            if(node[left-1].num_0!=left&&node[left-1].num_1!=left)
                flag=false;
        if(left+k-1!=n-1)
            if((node[n-1].num_0-node[left+k-1].num_0!=(n-1-(left+k-1)))&&(node[n-1].num_1-node[left+k-1].num_1!=(n-1-(left+k-1))))
                flag=false;
        if(flag&&left!=0&&left+k-1!=n-1)
            if(node[0].item!=node[n-1].item)
                flag=false;
        if(flag)
            return true;
    }
    return false;
}

bool judge_second()
{
    bool answer=true;
    if(2*k<n||k==1)
        return false;
    for(int left=0;left+k-1<=n-1;left++)
    {
        bool temp_answer=false;
        bool flag_1=true,flag_2=true;
        if(left!=0)
            if(node[left-1].num_0!=left&&node[left-1].num_1!=left)
                flag_1=false;
        if(left+k-1!=n-1)
            if((node[n-1].num_0-node[left+k-1].num_0!=(n-1-(left+k-1)))&&(node[n-1].num_1-node[left+k-1].num_1!=(n-1-(left+k-1))))
                flag_2=false;
        if(left==0||left+k-1==n-1)
            temp_answer=true;
        if(left!=0&&left+k-1!=n-1&&flag_1&&flag_2)
            if((node[0].item==0&&node[n-1].item==1)||(node[0].item==1&&node[n-1].item==0))
                temp_answer=true;
        if(!temp_answer)
            answer=false;
    }
    return answer;
}

int main()
{

    scanf("%d%d",&n,&k);
    scanf("%s",s);
    node[0].item=s[0]-'0';
    node[0].num_0=node[0].num_1=0;
    if(node[0].item==0)
        node[0].num_0++;
    else
        node[0].num_1++;
    for(int i=1;i<n;i++)
    {
        node[i]=node[i-1];
        node[i].item=s[i]-'0';
        if(node[i].item==0)
            node[i].num_0++;
        else
            node[i].num_1++;
    }
    if(judge_first())
        printf("tokitsukaze\n");
    else if(judge_second())
        printf("quailty\n");
    else
        printf("once again\n");
    return 0;
}

写于2019年7月30日

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值