1. 程式人生 > >B:魔獸世界之一:備戰

B:魔獸世界之一:備戰

描述

魔獸世界的西面是紅魔軍的司令部,東面是藍魔軍的司令部。兩個司令部之間是依次排列的若干城市。 
紅司令部,City 1,City 2,……,City n,藍司令部

兩軍的司令部都會製造武士。武士一共有 dragon 、ninja、iceman、lion、wolf 五種。每種武士都有編號、生命值、攻擊力這三種屬性。 

雙方的武士編號都是從1開始計算。紅方製造出來的第n個武士,編號就是n。同樣,藍方製造出來的第n個武士,編號也是n。 

武士在剛降生的時候有一個生命值。 

在每個整點,雙方的司令部中各有一個武士降生。 

紅方司令部按照iceman、lion、wolf、ninja、dragon的順序迴圈制造武士。 

藍方司令部按照lion、dragon、ninja、iceman、wolf的順序迴圈制造武士。 

製造武士需要生命元。 

製造一個初始生命值為m的武士,司令部中的生命元就要減少m個。 

如果司令部中的生命元不足以製造某個按順序應該製造的武士,那麼司令部就試圖製造下一個。如果所有武士都不能製造了,則司令部停止製造武士。

給定一個時間,和雙方司令部的初始生命元數目,要求你將從0點0分開始到雙方司令部停止製造武士為止的所有事件按順序輸出。
一共有兩種事件,其對應的輸出樣例如下: 

1) 武士降生 
輸出樣例: 004 blue lion 5 born with strength 5,2 lion in red headquarter
表示在4點整,編號為5的藍魔lion武士降生,它降生時生命值為5,降生後藍魔司令部裡共有2個lion武士。(為簡單起見,不考慮單詞的複數形式)注意,每製造出一個新的武士,都要輸出此時司令部裡共有多少個該種武士。

2) 司令部停止製造武士
輸出樣例: 010 red headquarter stops making warriors
表示在10點整,紅方司令部停止製造武士

輸出事件時: 

首先按時間順序輸出; 

同一時間發生的事件,先輸出紅司令部的,再輸出藍司令部的。

輸入第一行是一個整數,代表測試資料組數。

每組測試資料共兩行。 

第一行:一個整數M。其含義為, 每個司令部一開始都有M個生命元( 1 <= M <= 10000)。

第二行:五個整數,依次是 dragon 、ninja、iceman、lion、wolf 的初始生命值。它們都大於0小於等於10000。輸出對每組測試資料,要求輸出從0時0分開始,到雙方司令部都停止製造武士為止的所有事件。
對每組測試資料,首先輸出"Case:n" n是測試資料的編號,從1開始 。
接下來按恰當的順序和格式輸出所有事件。每個事件都以事件發生的時間開頭,時間以小時為單位,有三位。樣例輸入

1
20
3 4 5 6 7

樣例輸出

Case:1
000 red iceman 1 born with strength 5,1 iceman in red headquarter
000 blue lion 1 born with strength 6,1 lion in blue headquarter
001 red lion 2 born with strength 6,1 lion in red headquarter
001 blue dragon 2 born with strength 3,1 dragon in blue headquarter
002 red wolf 3 born with strength 7,1 wolf in red headquarter
002 blue ninja 3 born with strength 4,1 ninja in blue headquarter
003 red headquarter stops making warriors
003 blue iceman 4 born with strength 5,1 iceman in blue headquarter
004 blue headquarter stops making warriors

 

對面向物件真的是沒有一點思路呀,看著答案自己把程式碼寫了一下。

Code:

#include <iostream>
#include <cstring>
#include <string>
using namespace std;
const int WARRIOR_NUM = 5;  //士兵數量

class Headquarter;
class Warrior {
    private:
        Headquarter * pHeadquarter;
        int kindNo;     //武士種類編號
        int no;

    public:
        static string names[WARRIOR_NUM];
        static int initialLifeValue[WARRIOR_NUM];
        Warrior(Headquarter * p, int no, int kindNo_);
        void PrintResult(int nTime);
};

class Headquarter {
    private:
        int totalLifeValue;
        bool stopped;
        int totalWarriorNum;
        int color;
        int curMakingSeqIdx;
        int warriorNum[WARRIOR_NUM];
        Warrior * pWarriors[1000];
    public:
        friend class Warrior;
        static int makingSeq[2][WARRIOR_NUM];
        void Init(int color_, int lv);
        ~Headquarter();
        int Produce(int nTime);
        string GetColor();
};

Warrior::Warrior(Headquarter * p, int no_, int kindNo_) {   //Warrior類的建構函式
    no = no_;
    kindNo = kindNo_;
    pHeadquarter = p;
}

void Warrior::PrintResult(int nTime) {
    string color = pHeadquarter->GetColor();
    printf("%03d %s %s %d born with strength %d,%d %s in %s headquarter\n",
            nTime, color.c_str(), names[kindNo].c_str(), no, initialLifeValue[kindNo],
            pHeadquarter->warriorNum[kindNo], names[kindNo].c_str(), color.c_str());
}

void Headquarter::Init(int color_, int lv) {
    color = color_;
    totalLifeValue = lv;
    totalWarriorNum = 0;
    stopped = false;
    curMakingSeqIdx = 0;
    for (int i = 0; i < WARRIOR_NUM; ++i) {
        warriorNum[i] = 0;
    }
}

Headquarter::~Headquarter() {
    for (int i = 0; i < totalWarriorNum; ++i) {
        delete pWarriors[i];
    }
}

int Headquarter::Produce(int nTime) {
    if (stopped) return 0;
    int searchingTimes = 0;
    while (Warrior::initialLifeValue[makingSeq[color][curMakingSeqIdx]] > totalLifeValue &&
           searchingTimes < WARRIOR_NUM) {
        curMakingSeqIdx = (curMakingSeqIdx + 1) % WARRIOR_NUM;
        searchingTimes++;
    }
    int kindNo = makingSeq[color][curMakingSeqIdx];
    if (Warrior::initialLifeValue[kindNo] > totalLifeValue) {
        stopped = true;
        if (color == 0)
            printf("%03d red headquarter stops making warriors\n", nTime);
        else
            printf("%03d blue headquarter stops making warriors\n", nTime);
        return 0;
    }

    totalLifeValue -= Warrior::initialLifeValue[kindNo];
    curMakingSeqIdx = (curMakingSeqIdx + 1) % WARRIOR_NUM;
    pWarriors[totalWarriorNum] = new Warrior(this, totalWarriorNum+1, kindNo);
    warriorNum[kindNo]++;
    pWarriors[totalWarriorNum]->PrintResult(nTime);
    totalWarriorNum++;
    return 1;
}

string Headquarter::GetColor() {
    if (color == 0) return "red";
    else return "blue";
}

string Warrior::names[WARRIOR_NUM] = {"dragon", "ninja", "iceman", "lion", "wolf"};
int Warrior::initialLifeValue[WARRIOR_NUM];
int Headquarter::makingSeq[2][WARRIOR_NUM] = {{2, 3, 4, 1, 0}, {3, 0, 1, 2, 4}};

int main()
{
    int t;
    int m;
    Headquarter RedHead, BlueHead;
    scanf("%d", &t);
    int nCaseNo = 1;
    while (t--) {
        printf("Case:%d\n", nCaseNo++);
        scanf("%d", &m);
        for (int i = 0; i < WARRIOR_NUM; ++i) {
            scanf("%d", &Warrior::initialLifeValue[i]);
        }
        RedHead.Init(0, m);
        BlueHead.Init(1, m);
        int nTime = 0;
        while (true) {
            int tmp1 = RedHead.Produce(nTime);
            int tmp2 = BlueHead.Produce(nTime);
            if (tmp1 == 0 && tmp2 == 0) break;
            nTime++;
        }
    }
    return 0;
}