HihoCode 1531 : 德国心脏病

Posted 可达龙

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了HihoCode 1531 : 德国心脏病相关的知识,希望对你有一定的参考价值。

时间限制:10000ms

单点时限:1000ms

内存限制:256MB

描述

Jack在和朋友们玩德国心脏病。

德国心脏病的游戏牌分为水果牌和动物牌。水果只有4种:香蕉、草莓、樱桃、柠檬,每张水果牌上会有种类不定、总数目1-5的水果;动物只有3种:猴子、大象、猪,每张动物牌上有且仅有一只动物。

n名玩家绕圈就座,第一轮游戏从0号至n-1号轮流出牌。每个玩家面前最多只有一张牌,如果玩家出牌时,他的面前已经摆放了一张牌,他新出的牌将会严丝合缝地盖住旧牌。

任何时候玩家可以选择按铃操作。如果按铃成功,玩家可以获得当前场上所有牌(包括被盖住的牌)并进入下一轮游戏,下一轮游戏由他先出牌,然后依序轮流出牌;否则,他需要支付给每位玩家一张手牌,然后他成为下一位出牌者,继续这一局游戏。

按铃成功的条件:

1、当前场上(被盖住的牌不算,以下同)某种水果的数量正好为5。

2、当前场上出现猴子,至少有一个水果,且没有出现柠檬。

3、当前场上出现大象,至少有一个水果,且没有出现草莓。

4、当前场上出现猪,且至少有一个水果。

Bob对这个游戏很感兴趣,他给了Jack一个操作序列,希望Jack输出最终每个人拥有的牌的数量。每名玩家初始拥有10,000,000张牌。操作分为两种:出牌或按铃。操作结束时游戏立即终止。

1、出牌的格式是:Fruit+水果数s+水果种类*s,0、1、2、3分别表示香蕉、草莓、樱桃、柠檬。如Fruit 4 0 2 2 2代表1个香蕉和3个樱桃的牌。或Animal+动物种类,0、1、2分别代表猴子、大象、猪。如Animal 0代表一张猴子牌。注意,选手需要自己计算出牌者是几号玩家。

2、按铃的格式是:Ring+选手编号。如Ring 2。

输入

第一行两个正整数n(≤10), k(≤100,000)。

接下来k行,每行对应一个操作。

输出

n行,每行一个整数,代表每个玩家游戏结束后拥有的牌的数目。

样例解释

3 13 # 井号后为样例输入说明:3名玩家,13次操作 Fruit 5 0 0 0 0 0 # 0号玩家出牌:5个香蕉 Ring 0 # 0号玩家按铃:按铃成功,获得场上的1张牌,开始下一轮游戏 Ring 1 # 1号玩家按铃:按铃失败,给0, 2号玩家各一张牌 Fruit 3 3 0 0 # 1号玩家出牌:1个柠檬+2个香蕉 Animal 0 # 2号玩家出牌:猴子 Fruit 4 2 2 2 2 # 0号玩家出牌:4个樱桃 Ring 2 # 2号玩家按铃:按铃失败,给0, 1号玩家各一张牌 Fruit 3 0 0 0 # 2号玩家出牌:3个香蕉,盖住上一张牌【猴子】 Fruit 2 0 0 # 0号玩家出牌:2个香蕉,盖住上一张牌【4个樱桃】 Ring 2 # 2号玩家按铃:按铃失败,给0, 1号玩家各一张牌 Animal 2 # 2号玩家出牌:猪,盖住上一张牌【3个香蕉】 Ring 0 # 0号玩家按铃:按铃成功,获得场上的6张牌,开始下一轮游戏 Animal 2 # 0号玩家出牌:猪,游戏终止

样例输入 3 13 Fruit 5 0 0 0 0 0 Ring 0 Ring 1 Fruit 3 3 0 0 Animal 0 Fruit 4 2 2 2 2 Ring 2 Fruit 3 0 0 0 Fruit 2 0 0 Ring 2 Animal 2 Ring 0 Animal 2样例输出 10000006 9999999 9999994一个简单的模拟。模拟两种动作,出牌和按铃。定义场上存在的牌面,因为会覆盖所以只要最后一次的牌面,一个N长度的数组就可以。加上一个数组表示每个人桌子上自己跟前有几张牌,一个数组记录每个人手里有几张牌。还有一个记录出牌人编号的游标。每次要对人数取模。出牌的时候,清空自己的牌面,重新为牌面赋值,桌子上牌数量加一,手里牌数量减一。然后下一个人。按铃的时候,单独函数判断牌面是否能按铃成功,然后处理。最后要把游标放到当前位置上。

#include <iostream>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
using namespace std;
const int INF = 0x3f3f3f3f;
typedef long long LL;

const int N = 10 + 3;

int n, k;
int owncard[N];
struct Card
{
    int type;
    int friut[4];
    int animial[3];
};

Card Up[N];
int cardtotal[N];

void init()
{
    for(int i = 0; i < n; i++)
    {
        owncard[i] = 10000000;
        cardtotal[i] = 0; //桌上card
    }
    memset(Up, 0, sizeof(Up));
}

char Type[30];

int judge(int num)
{
    int totalfriut[4] = {0,0,0,0};
    for(int i = 0; i < n; i++)
    {
        for(int j = 0; j < 4; j++)
            totalfriut[j] += Up[i].friut[j];
    }
    for(int i = 0; i < 4; i++)
    {
        if(totalfriut[i] == 5)
            return 1;
    }

    int monkey = 0, pig = 0, elephent = 0;

    for(int i = 0; i < n; i++)
    {
        if(Up[i].animial[0]) monkey = 1;
        if(Up[i].animial[1]) elephent = 1;
        if(Up[i].animial[2]) pig = 1;
    }

    if(monkey && totalfriut[3] == 0 &&
        (totalfriut[0] || totalfriut[1] || totalfriut[2]) )
        return 1;
    if(elephent && totalfriut[1] == 0 &&
        (totalfriut[0] || totalfriut[3] || totalfriut[2]) )
        return 1;
    if(pig && (totalfriut[0] || totalfriut[3] || totalfriut[2] || totalfriut[1]))
        return 1;
    return 0;
}

void solve()
{

    scanf("%d%d", &n, &k);
    init();
    int cur = 0;
    for(int i = 0; i < k ; i++)
    {
        cur = cur % n;
        scanf("%s", Type);
        if(Type[0] == F)
        {
            owncard[cur]--;
            cardtotal[cur]++;
            Up[cur].type = 1;
            Up[cur].friut[0] = Up[cur].friut[1] = 0;
            Up[cur].friut[2] = Up[cur].friut[3] = 0;
            Up[cur].animial[0] = Up[cur].animial[1] = Up[cur].animial[2] = 0;

            int num,f;
            scanf("%d", &num);
            for(int j = 0; j < num; j++)
            {
                scanf("%d", &f);
                Up[cur].friut[f]++;
            }

            cur++;
        }
        else if(Type[0] == A)
        {
            owncard[cur]--;
            cardtotal[cur]++;

            Up[cur].type = 2;
            Up[cur].friut[0] = Up[cur].friut[1] = 0;
            Up[cur].friut[2] = Up[cur].friut[3] = 0;
            Up[cur].animial[0] = Up[cur].animial[1] = Up[cur].animial[2] = 0;

            int num;
            scanf("%d", &num);
            Up[cur].animial[num] = 1;

            cur++;
        }
        else if(Type[0] == R)
        {
            int num;
            scanf("%d", &num);
            int isok = judge(num);
            if(isok)
            {
                for(int j = 0; j < n; j++)
                {
                    owncard[num] += cardtotal[j];
                    cardtotal[j] = 0;
                }
                memset(Up, 0, sizeof(Up));
                cur = num;
            }
            else
            {
                for(int j = 0; j < n; j++)
                {
                    if(j != num)
                    {
                        owncard[num] -- ;
                        owncard[j] ++;
                    }
                }
                cur = num;
            }
        }
    }
    for(int i = 0; i < n; i++)
        printf("%d\n", owncard[i]);
}

int main()
{
    solve();
    return 0;
}

 

以上是关于HihoCode 1531 : 德国心脏病的主要内容,如果未能解决你的问题,请参考以下文章

世界第一辐轮王土拨鼠6453万美国德国碳纤维自行车品牌排行榜

hihocode #1388 : Periodic Signal NTT

Hihocode 1304

HihoCode-1053-居民迁移

hihocode#1174(拓扑排序判环模板)

hihocode 1584 : Bounce (找规律)(2017 北京网络赛G)