I believe sorting the poker at first may be helpful. You should determine the kind of the poker hand from the highest rank down to the lowest. Comparing the poker hands with the same kind is tricky to implement due to the complex rules.
Code:
- /*************************************************************************
- * Copyright (C) 2008 by liukaipeng *
- * liukaipeng at gmail dot com *
- *************************************************************************/
- /* @JUDGE_ID 00000 10315 C "Poker Hands" */
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <strings.h>
- #define NVALUES 13
- #define NSUITS 4
- enum {
- HC, PR, TP, TK, ST, FL, FH, FK, SF,
- };
- void rank(int values[], char suits[], int rank[])
- {
- int i, j;
- int count[NVALUES] = {0};
- int flush;
- int straight;
- int pair = 0;
- int three = 0;
- int four = 0;
- int kind;
- for (i = 0; i < 5; ++i)
- count[values[i]] += 1;
- for (i = 0; i < 5; ++i) {
- for (j = 0; j < 5-i-1; ++j) {
- if (values[j] < values[j+1]) {
- values[j] ^= values[j+1];
- values[j+1] ^= values[j];
- values[j] ^= values[j+1];
- }
- }
- }
- straight = values[0] - values[1] == 1 && values[1] - values[2] == 1 &&
- values[2] - values[3] == 1 && values[3] - values[4] == 1;
- flush = suits[0] == suits[1] && suits[1] == suits[2] &&
- suits[2] == suits[3] && suits[3] == suits[4];
- for (i = 0; i < NVALUES; ++i) {
- if (count[i] == 2)
- pair += 1;
- else if (count[i] == 3)
- three += 1;
- else if (count[i] == 4)
- four += 1;
- }
- if (straight && flush)
- kind = SF;
- else if (four)
- kind = FK;
- else if (three && pair)
- kind = FH;
- else if (flush)
- kind = FL;
- else if (straight)
- kind = ST;
- else if (three)
- kind = TK;
- else if (pair == 2)
- kind = TP;
- else if (pair)
- kind = PR;
- else
- kind = HC;
- rank[0] = kind;
- switch (kind) {
- case HC: case FL:
- for (i = 0; i < 5; ++i)
- rank[i+1] = values[i];
- break;
- case ST: case SF:
- rank[1] = values[0];
- break;
- case FK:
- if (values[0] == values[1])
- rank[1] = values[0];
- else
- rank[1] = values[1];
- break;
- case FH:
- if (values[0] == values[1] && values[1] == values[2])
- rank[1] = values[0];
- else
- rank[1] = values[2];
- break;
- case TK:
- if (values[0] == values[1])
- rank[1] = values[0];
- else if (values[1] == values[2])
- rank[1] = values[1];
- else
- rank[1] = values[2];
- break;
- case PR:
- for (i = 0, j = 2; i < 4; ++i)
- if (values[i] == values[i+1])
- rank[1] = values[i++];
- else
- rank[j++] = values[i];
- break;
- case TP:
- for (i = 0, j = 3; i < 4; ++i)
- if (values[i] == values[i+1])
- rank[1] = values[i++];
- else
- rank[j++] = values[i];
- if (rank[1] < rank[2])
- rank[1] ^= rank[2], rank[2] ^= rank[1], rank[1] ^= rank[2];
- break;
- default:
- break;
- }
- }
- int compare(int bvalues[], char bsuits[], int wvalues[], char wsuits[])
- {
- int brank[6] = {-1, -1, -1, -1, -1, -1, };
- int wrank[6] = {-1, -1, -1, -1, -1, -1, };
- int i;
- rank(bvalues, bsuits, brank);
- rank(wvalues, wsuits, wrank);
- for (i = 0; i < 6; ++i)
- if (brank[i] > wrank[i])
- return 0;
- else if (brank[i] < wrank[i])
- return 1;
- return 2;
- }
- int main(int argc, char *argv[])
- {
- #ifndef ONLINE_JUDGE
- char in[256];
- char out[256];
- strcpy(in, argv[0]);
- strcat(in, ".in");
- freopen(in, "r", stdin);
- strcpy(out, argv[0]);
- strcat(out, ".out");
- freopen(out, "w", stdout);
- #endif
- char *message[] = {
- "Black wins.",
- "White wins.",
- "Tie.",
- };
- char *cvalues = "23456789TJQKA";
- int values[128];
- int bvalues[5], wvalues[5];
- char bsuits[5], wsuits[5];
- char buf[40];
- int i;
- for (i = 0; i < NVALUES; ++i)
- values[cvalues[i]] = i;
- while (fgets(buf, 40, stdin) != NULL) {
- for (i = 0; i < 5; ++i) {
- bvalues[i] = values[buf[3*i]];
- bsuits[i] = buf[3*i+1];
- wvalues[i] = values[buf[3*i+3*5]];
- wsuits[i] = buf[3*i+3*5+1];
- }
- puts(message[compare(bvalues, bsuits, wvalues, wsuits)]);
- }
- return 0;
- }
本文介绍了一种用于识别扑克牌手类型的算法实现。通过对手中五张牌进行排序和分类,该算法能准确判断出手牌类型,如顺子、同花顺等,并据此比较两组手牌的胜负。
291

被折叠的 条评论
为什么被折叠?



