ZZULIOJ 1851: KILL By Assassin

来源:互联网 发布:org域名申请 编辑:程序博客网 时间:2024/05/20 13:36
Description众所周知,yjj发现了一款新型的益智卡牌游戏叫SGK,游戏的具体内容是这样的:(1)游戏方式:1.游戏玩家分为两人A和B,双方生命值均为3点且各拥有不超过9张的手牌。由玩家A主动出牌发起进攻,若玩家A能打败玩家B则算玩家A胜利,否则算玩家B胜利。2.游戏内打出的卡牌即为从手牌中丢弃。3.为了增加游戏的乐趣,双方的手牌均为互相可见。PS:1.玩家被打败的条件是生命值降为0,且没有恢复生命值的卡牌了。2.若玩家已被打败,则不能够再出牌。(2)卡牌类型:“杀”牌(K):1.直接打出一张指向对方,若对方不能打出一张“闪”牌进行响应,则对方损失一点生命值。(本方法只能使用一次)2.用来响应“南蛮入侵”牌。3.用来响应“决斗”牌。“闪”牌(S):1.用来响应“万箭齐发”牌。2.用来响应“杀”牌。“桃”牌(T):1.在生命值降为0的时候可自动打出,为该玩家恢复一点生命值。“南蛮入侵”牌(N):1.直接打出一张指向对方,若对方不能打出一张“杀”牌进行响应,则对方损失一点生命值。(本方法可以使用任意次)“万箭齐发”牌(W):1.直接打出一张指向对方,若对方不能打出一张“闪”牌进行响应,则对方损失一点生命值。(本方法可以使用任意次)“决斗”牌(J):1.直接打出一张指向对方,由对方开始双方轮流打出一张“杀”牌进行响应,直到其中一方不能够打出“杀”牌为止,则该方损失一点生命值。(本方法可以使用任意次)PS:1.用来响应的方法可以使用任意次。    2.若有牌可以响应则必须打出响应。今天yjj邀请JS和DZ来玩这个游戏,由JS作为玩家A,DZ作为玩家B。现在告诉你JS和DZ的手牌,聪明的你能告诉yjj谁能够胜利么?Input首先输入一个整数T,代表有T组测试实例。(1<=T<=100)对于每组测试,输入包含三行,第一行包含两个整数n、m,分别代表JS的手牌数和DZ的手牌数。(0<=n,m<=9)接下两行分别代表JS的牌型和DZ的牌型,牌型均为上述牌型括号内的大写字母,用空格隔开。Output对于每组测试实例,若JS胜利则输出“JS”,若DZ胜利则输出“DZ”(不带引号)。Sample Input24 1K K K KS4 1W W W WSSample OutputDZJS

思路:传统的三国杀游戏,这里题目中需要注意的几点


1.JS为玩家A,为先手
2.A的获胜条件,只有A在第一回合杀死B才算胜利

那么我们只需要考录A的出牌顺序,判断能否杀掉B即可。那么具体怎么考虑呢?仔细思考,只要尽可能多的杀掉对方的血即可。我们遵守下面的逻辑顺序


1.首先桃子是无差别的,每个人第一回合最大生命值(可能会超过三点)相当于每个人的血量加拥有的桃子数量
2.将万箭齐发放完,因为万箭齐发B只能用闪响应,且不可能对A造成伤害
3.判断此时B是否有闪,如果有闪,则不出杀,因为出杀没有意义,消耗对方一个闪不会造成伤害,我们的万箭齐发也用完,对方也不再需要用闪躲避攻击了。而且我们不出杀节省下来的杀可以留着后面决斗用!相反,如果对方没有闪,我们出杀,砍掉B一点血
4.为了给对方造成最大的杀伤,假如我们的决斗和杀够,先使用决斗,手中有杀就响应,直到A被杀成1滴血或者是对方死亡
5.这个时候A的决斗已经最大可能的消耗了B的杀,此时A将南蛮入侵全部放完杀伤最优
6.这个时候如果对方还没死,我们手中只有决斗了,那么如果将对方决斗死了且自己没死,就A胜,否则A一定就输了

理清了就很简单了,下面是我的丑代码,主要是每一步的时候将,对应的剩余牌数、血量变化清楚即可

#include<bits/stdc++.h>using namespace std;int k[2],s[2],n[2],w[2],t[2],j[2],life[2];void add(char sign,int pos){    if(sign=='K')       k[pos]++;    else if(sign=='S')  s[pos]++;    else if(sign=='N')  n[pos]++;    else if(sign=='W')  w[pos]++;    else if(sign=='J')  j[pos]++;    else if(sign=='T')  t[pos]++;}int main(){    //freopen("input.txt","r",stdin);    int T,k1,k2;    string sign;    scanf("%d",&T);    while(T--){        k[0]=k[1]=s[0]=s[1]=n[0]=n[1]=0;        w[0]=w[1]=t[0]=t[1]=j[0]=j[1]=0;        life[0]=life[1]=3;        scanf("%d%d",&k1,&k2);        for(int i=1;i<=k1;i++){            cin>>sign;            add(sign[0],0);        }        for(int i=1;i<=k2;i++){            cin>>sign;            add(sign[0],1);        }        life[0]+=t[0];        life[1]+=t[1];        if(w[0]<=s[1]) {                    //全部放万箭齐发             s[1]-=w[0];            w[0]=0;        }        else {            life[1]-=(w[0]-s[1]);            w[0]=0;            s[1]=0;        }        if(life[1]<=0) {            cout<<"JS"<<endl;            continue;        }        if(s[1]==0&&k[0]>0){                //如果B没有闪了,杀有用 ,否则是不变的            life[1]--;            k[0]--;        }        if(life[1]<=0) {            cout<<"JS"<<endl;            continue;        }        while(life[0]>1&&j[0]>0){           //先决斗消耗杀 ,前提是保证自己没死            if(k[0]>=k[1]){                life[1]--;                k[0]-=k[1];                k[1]=0;            }            else {                k[1]-=(k[0]+1);                k[0]=0;                life[0]--;            }            j[0]--;            if(life[1]<=0) break;           //把B砍死了也就结束了        }        if(life[1]<=0) {            cout<<"JS"<<endl;            continue;        }        if(n[0]>=k[1]){                     //再放所有南蛮             life[1]-=(n[0]-k[1]);            n[0]=0;            k[1]=0;        }        else {            n[0]=0;            k[1]-=n[0];        }        if(life[1]<=0) {            cout<<"JS"<<endl;            continue;        }        while(life[0]>0&&life[1]>0&&j[0]>0){    //放出所有决斗,知道有人死或者决斗放完            if(k[0]>=k[1]){                life[1]--;                k[0]-=k[1];                k[1]=0;            }            else {                k[1]-=(k[0]+1);                life[0]--;            }            j[0]--;        }         if(life[1]<=0) {            cout<<"JS"<<endl;            continue;        }        cout<<"DZ"<<endl;    }    return 0;}
0 0
原创粉丝点击