2015华为软赛(五)——基本功能函数

来源:互联网 发布:怎么改淘宝店铺名字 编辑:程序博客网 时间:2024/05/23 13:20

点滴记录总结,一天一打鸡血。

2015年5月华为组织了一次软件精英挑战赛,赛题是德州扑克手牌AI~

环境及测试说明:http://pan.baidu.com/s/1dD2dL0P

这一节说一些基本的功能函数,又是基本,对的,在此基础上,下一节会给点比介个复杂点的函数。说起来真是惭愧,没有像李博士、收割机之流有那么高大的算法,要说算法的话,倒是有个,rand()!!!想想研一的概率算法算是白学了,囧~~

先回忆一下基本流程,是这样:

  1. 向服务器注册(连接部分之前说过);
  2. 服务器发送座次信息,需要识别,这节不讨论;
  3. HOLD圈服务器发送手牌信息(2张),需要识别,在此讨论;
  4. 服务器发送inquire消息,不讨论;
  5. 手牌发送决策,不讨论;
  6. FLOP圈服务器发送公牌消息(3张),需要识别,在此讨论;
  7. 同4、5;
  8. TURN圈发送公牌消息(1张),需要识别,在此讨论;
  9. 同4、5;
  10. RIVER圈发送公牌消息(1张),需要识别,在此讨论;
  11. 同4、5。

这一节主要辨识牌型,识别牌力。于是给出了下面这些函数:

void    UpdateCards (const char *recv, int flag);void    UpdateCardType (int flag);void    FlopCardType ();void    TurnCardType ();void    RiverCardType ();int     IsStraight(int card[], int start, int len);int     IsFlush(int type[],int start, int len);int     IsFour(int card[], int start, int len);int     Max(int x, int y);

上面函数不需要过多解释,名字起的好就是省事呐。

函数UpdateCards (const char *recv, int flag)的参数flag表示那一圈,针对不同圈,更新不同变量,比如FLOP圈,手牌会收到下面这样的消息:

flop/ CLUBS 7 CLUBS J DIAMONDS 9 /flop 

这之前已经收到手牌了,一共五张牌,接下来要UpdateCards,用switch-case结构来处理:

//此处省略...case FLOP:        recv = recv + 7;        for (i=0; i<3; i++) {//3张牌            switch (*recv) {//以第一个字符识别花色                case 'S':                    cardType = SPADES;break;                case 'H':                    cardType = HEARTS;break;                case 'C':                    cardType = CLUBS;break;                case 'D':                    cardType = DIAMONDS;break;            }            pos = 0;            while (*(recv+pos) != ' ')                pos++;            recv = recv + pos + 1;            pos = 0;            memset(data, '\0', DATA_SIZE);            while (*(recv+pos) != ' ')                pos++;            strncpy(data, recv, pos);            switch (data[0]) {                case 'J':                    cardValue = 10;break;                case 'Q':                    cardValue = 11;break;                case 'K':                    cardValue = 12;break;                case 'A':                    cardValue = 13;break;                default:                    cardValue = atoi(data) - 1;break;// 牌值2表示1..类推            }            common_cards[i] = cardType * 14 + cardValue;            recv = recv + pos + 2;        }        //set game_circle to FLOP        game_circle = FLOP;//告诉自己,现在已经到FLOP圈,方便后续决策        UpdateCardType(FLOP);//完了还得更新自己的牌力    break;

消息的处理是一些简单字符串处理,简单但是不能有丝毫差错!其他圈的牌型类似,再说说更新牌力函数,列下来:

void UpdateCardType (int flag) {    switch(flag) {        case FLOP:            FlopCardType();        break;        case TURN:            TurnCardType();        break;        case RIVER:            RiverCardType();        break;    }}//调用FlopCardType(),下面的代码量比较大,使用伪码吧void    FlopCardType () {    card[5]//已经辨识了五张牌值    type[5]//牌的花色    high_card<--Max(card[5])    //if four    four.own = IsFour(card[5]);    if(four.own == 0) {//不为零就是大牌,没必要再辨识了        s_card.owm = IsStraight(card[5])//顺子        f_card.owm = IsFlush(type[5])//同花        three = card[5]//三条        pair[2] = card[5]//两对        pair[1] = card[5]//一对    }    if(three!=0 && pair!=0)        my_type = FULLHOUSE;    else if (three != 0)        my_type = THREE;    else if (pair[2] != 0)        my_type = TWOPAIR;    else if (pair[1] != 0)        my_type = ONEPAIR;    else        my_type = HIGH_CARD;}

也看到上面的函数部分使用了,IsFour、IsStraight、IsFlush等,实现比较傻,判定时间够用,也没去想着优化了。给一个IsFour的实现,其它类似啦。

//这样带参数有好处,就是每个圈判定只需要不同参数即可,//比如RIVER圈,start=0,len=7,因为有五张手牌,这样可以判定four.own,//那么four.com可以设定start=2,len=5,因为前两张牌是自己手牌,后面五张牌才是公牌~~~~int     IsFour(int card[],int start, int len) {    int i, j, k, m, n;    int four = 0;    for (i=start; i<start+len; ++i){    for (j=start; j<start+len; ++j){        if(j != i) {        for (k=start; k<start+len; ++k){            if(k!=i && k!=j){            for (m=start; m<start+len; ++m){                if(m!=i && m!=j && m!=k) {                    if (card[i] == card[j] &&                        card[i] == card[k] &&                         card[i] == card[m] ){                        four = card[i];                        break;                        }                    }                if(four!=0) break;                }}            if(four!=0) break;            }}        if(four!=0) break;        }    if(four!=0) break;    }       if(four!=0)        return four;    return 0;}

基本函数完。

0 0
原创粉丝点击