int enumSample(enum_game_t game, StdDeck_CardMask pockets[], StdDeck_CardMask board, StdDeck_CardMask dead, int npockets, int nboard, int niter, int orderflag, enum_result_t *result) { int numCards; enumResultClear(result); if (npockets > ENUM_MAXPLAYERS) return 1; if (orderflag) { enum_ordering_mode_t mode; switch (game) { case game_holdem: case game_omaha: case game_7stud: case game_5draw: mode = enum_ordering_mode_hi; break; case game_razz: case game_lowball: case game_lowball27: mode = enum_ordering_mode_lo; break; case game_holdem8: case game_omaha8: case game_7stud8: case game_7studnsq: case game_5draw8: case game_5drawnsq: mode = enum_ordering_mode_hilo; break; default: return 1; } if (enumResultAlloc(result, npockets, mode)) return 1; } if (game == game_holdem) { StdDeck_CardMask sharedCards; numCards = 5 - nboard; if (numCards > 0) { DECK_MONTECARLO_N_CARDS_D(StdDeck, sharedCards, dead, numCards, niter, INNER_LOOP_HOLDEM); } else { StdDeck_CardMask_RESET(sharedCards); INNER_LOOP_HOLDEM; return 1; } } else { return 1; } result->game = game; result->nplayers = npockets; result->sampleType = ENUM_SAMPLE; return 0; }
int enumExhaustive(enum_game_t game, StdDeck_CardMask pockets[], StdDeck_CardMask board, StdDeck_CardMask dead, int npockets, int nboard, int orderflag, enum_result_t *result) { enumResultClear(result); if (npockets > ENUM_MAXPLAYERS) return 1; if (orderflag) { enum_ordering_mode_t mode; switch (game) { case game_holdem: case game_omaha: case game_7stud: case game_5draw: mode = enum_ordering_mode_hi; break; case game_razz: case game_lowball: case game_lowball27: mode = enum_ordering_mode_lo; break; case game_holdem8: case game_omaha8: case game_7stud8: case game_7studnsq: case game_5draw8: case game_5drawnsq: mode = enum_ordering_mode_hilo; break; default: return 1; } if (enumResultAlloc(result, npockets, mode)) return 1; } if (game == game_holdem) { StdDeck_CardMask sharedCards; if (nboard == 0) { DECK_ENUMERATE_5_CARDS_D(StdDeck, sharedCards, dead, INNER_LOOP_HOLDEM); } else if (nboard == 3) { DECK_ENUMERATE_2_CARDS_D(StdDeck, sharedCards, dead, INNER_LOOP_HOLDEM); } else if (nboard == 4) { DECK_ENUMERATE_1_CARDS_D(StdDeck, sharedCards, dead, INNER_LOOP_HOLDEM); } else if (nboard == 5) { StdDeck_CardMask_RESET(sharedCards); INNER_LOOP_HOLDEM; } else { return 1; } } else { return 1; } result->game = game; result->nplayers = npockets; result->sampleType = ENUM_EXHAUSTIVE; return 0; }
int main(int argc, char **argv) { enum_game_t game; enum_sample_t enumType; int niter = 0, npockets, nboard, err, terse, orderflag; StdDeck_CardMask pockets[ENUM_MAXPLAYERS]; StdDeck_CardMask board; StdDeck_CardMask dead; enum_result_t result; int fromStdin; fromStdin = (argc == 2 && !strcmp(argv[1], "-i")); if (fromStdin) argv = (char **) malloc(MAX_ARGS * sizeof(char *)); do { err = 0; enumResultClear(&result); if (fromStdin) { /* read one line from stdin, split into argv/argc */ char buf[BUF_LEN], *p; if (fgets(buf, sizeof(buf), stdin) == NULL) break; argc = 0; argv[argc++] = "pokenum"; p = strtok(buf, " \t\r\n"); while (p != NULL) { argv[argc++] = p; p = strtok(NULL, " \t\r\n"); } } if (parseArgs(argc, argv, &game, &enumType, &niter, pockets, &board, &dead, &npockets, &nboard, &orderflag, &terse)) { if (fromStdin) { printf("ERROR\n"); } else { printf("single usage: %s [-t] [-O] [-mc niter]\n", argv[0]); printf("\t[-h|-h8|-o|-o8|-7s|-7s8|-7snsq|-r|-5d|-5d8|-5dnsq|-l|-l27]\n"); printf("\t<pocket1> - <pocket2> - ... [ -- <board> ] [ / <dead> ] ]\n"); printf("streaming usage: %s -i < argsfile\n", argv[0]); } err = 1; } else { if (enumType == ENUM_EXHAUSTIVE) { err = enumExhaustive(game, pockets, board, dead, npockets, nboard, orderflag, &result); } else if (enumType == ENUM_SAMPLE) { err = enumSample(game, pockets, board, dead, npockets, nboard, niter, orderflag, &result); } else { err = 1; } if (err) { if (fromStdin) printf("ERROR\n"); else printf("enumeration function failed err=%d\n", err); } else { if (terse) enumResultPrintTerse(&result, pockets, board); else enumResultPrint(&result, pockets, board); } } enumResultFree(&result); fflush(stdout); } while (fromStdin); return err; }
static int pyenumSample(enum_game_t game, StdDeck_CardMask pockets[], int numToDeal[], StdDeck_CardMask board, StdDeck_CardMask dead, int sizeToDeal, int iterations, enum_result_t *result) { int i; enumResultClear(result); StdDeck_CardMask cardsDealt[ENUM_MAXPLAYERS + 1]; memset(cardsDealt, 0, sizeof(StdDeck_CardMask) * (ENUM_MAXPLAYERS + 1)); if (sizeToDeal - 1 > ENUM_MAXPLAYERS) return 1; /* * Cards in pockets or in the board must not be dealt */ StdDeck_CardMask_OR(dead, dead, board); for(i = 0; i < sizeToDeal - 1; i++) { StdDeck_CardMask_OR(dead, dead, pockets[i]); } if (game == game_holdem) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_ANY_HIGH); } else if (game == game_holdem8) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_ANY_HILO); } else if (game == game_omaha) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_OMAHA); } else if (game == game_omaha8) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_OMAHA8); } else if (game == game_7stud) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_ANY_HIGH); } else if (game == game_7stud8) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_ANY_HILO); } else if (game == game_7studnsq) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_7STUDNSQ); } else if (game == game_razz) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_RAZZ); } else if (game == game_lowball27) { DECK_MONTECARLO_PERMUTATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, iterations, INNER_LOOP_LOWBALL27); } else { return 1; } result->game = game; result->nplayers = sizeToDeal - 1; result->sampleType = ENUM_SAMPLE; return 0; }
static int pyenumExhaustive(enum_game_t game, StdDeck_CardMask pockets[], int numToDeal[], StdDeck_CardMask board, StdDeck_CardMask dead, int sizeToDeal, enum_result_t *result) { int totalToDeal = 0; int i; enumResultClear(result); StdDeck_CardMask cardsDealt[ENUM_MAXPLAYERS + 1]; memset(cardsDealt, 0, sizeof(StdDeck_CardMask) * (ENUM_MAXPLAYERS + 1)); if (sizeToDeal - 1 > ENUM_MAXPLAYERS) return 1; for(i = 0; i < sizeToDeal; i++) totalToDeal += numToDeal[i]; /* * Cards in pockets or in the board must not be dealt */ StdDeck_CardMask_OR(dead, dead, board); for(i = 0; i < sizeToDeal - 1; i++) { StdDeck_CardMask_OR(dead, dead, pockets[i]); } if (game == game_holdem) { if(totalToDeal > 0) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_ANY_HIGH); } else { INNER_LOOP_ANY_HIGH; } } else if (game == game_holdem8) { if(totalToDeal > 0) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_ANY_HILO); } else { INNER_LOOP_ANY_HILO; } } else if (game == game_omaha) { if(totalToDeal > 0) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_OMAHA); } else { INNER_LOOP_OMAHA; } } else if (game == game_omaha8) { if(totalToDeal > 0) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_OMAHA8); } else { INNER_LOOP_OMAHA8; } } else if (game == game_7stud) { if(totalToDeal > 0) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_ANY_HIGH); } else { INNER_LOOP_ANY_HIGH; } } else if (game == game_7stud8) { if(totalToDeal > 0) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_ANY_HILO); } else { INNER_LOOP_ANY_HILO; } } else if (game == game_7studnsq) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_7STUDNSQ); } else if (game == game_razz) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_RAZZ); } else if (game == game_lowball27) { DECK_ENUMERATE_COMBINATIONS_D(StdDeck, cardsDealt, sizeToDeal, numToDeal, dead, INNER_LOOP_LOWBALL27); } else { return 1; } result->game = game; result->nplayers = sizeToDeal - 1; result->sampleType = ENUM_EXHAUSTIVE; return 0; }
int main(int argc, char* argv[]) { enum_game_t game = game_razz; { enum_result_t result; StdDeck_CardMask board; StdDeck_CardMask dead; StdDeck_CardMask pockets[2]; char* hand0[] = { "Ad", "2d", "3d", "4d", "5d", "Tc", "Th" }; //char* hand1[] = { "Ac", "2c", "3c", "4c", "5c", "Tc", "Th" }; char* hand1[] = { "4d", "4c", "8d", "8c", "9d", "9c", "9h" }; enumResultClear(&result); CardMask_RESET(board); CardMask_RESET(dead); pockets[0] = Strings2CardMask(7, hand0); pockets[1] = Strings2CardMask(7, hand1); assert(enumExhaustive(game, pockets, board, dead, 2, 0 /* nboard */, 0 /* orderflag */, &result) == 0); if(verbose) enumResultPrint(&result, pockets, board); assert(result.ev[0] == 1.0); assert(result.ev[1] == 0.0); } { /* http://shipitfish.livejournal.com/59671.html If after removing straights and flushes, if hand X beats hand Y under normal poker rules, the hand Y beats hand X under razz. There should *never* be a case where one hand wins over another in both normal poker rules and razz (after removing straights and flushes). Therefore, 6s full of 5s loses 4s full of 8s in razz and likewise by the same logic 6s and 5s beat 4s and 8s in razz. 4s and 8s should definately *NOT* beat 6s and 5s in both 7-card stud and razz. If one hand wins in 7-card stud, the other hand wins in razz. It is that simple. */ enum_result_t result; StdDeck_CardMask board; StdDeck_CardMask dead; StdDeck_CardMask pockets[2]; char* hand0[] = { "5d", "5c", "6d", "6c", "7d", "7c", "7h" }; char* hand1[] = { "4d", "4c", "8d", "8c", "9d", "9c", "9h" }; enumResultClear(&result); CardMask_RESET(board); CardMask_RESET(dead); pockets[0] = Strings2CardMask(7, hand0); pockets[1] = Strings2CardMask(7, hand1); assert(enumExhaustive(game, pockets, board, dead, 2, 0 /* nboard */, 0 /* orderflag */, &result) == 0); if(verbose) enumResultPrint(&result, pockets, board); assert(result.ev[0] == 1.0); assert(result.ev[1] == 0.0); } return 0; }