Picking the best hand out of 7 cards(Poker Texas Hold'em)
I've implemented a Texas Hold'em game using C#.
I wrote classes like Card, Deck, Player, Table etc... For example: Player player1 = new Player("player1");
player1.Card1 = new Card(4, Symbol.Clubs, true);
player1.Card2 = new Card(5, Symbol.Clubs, true);
Card card1 = new Card(4, Symbol.Clubs, true);
Card card2 = new Card(7, Symbol.Hearts, true);
Card card3 = new Card(2, Symbol.Spades, true);
Card card4 = new Card(4, Symbol.Diamonds, true);
Card card5 = new Card(4, Symbol.Clubs, true);
Card[] tableCards = {card1, card2, card3, card4, card5};
I've also wrote some m开发者_运维技巧ethods for evaluate cards array, like IsFlush, IsStraight, IsPair and so on.
My question is how should I pick the best hand combination if I got 7 cards(2 hand, 5 from the table). In this code example it's {4,4,4,4,7}.Don't write your code against 5-card hands. Instead, write it in general. So,
ContainsStraightFlush
ContainsFourOfAKind
ContainsFullHouse
etc. would eat a collection of cards and return true if some subset of those cards is a straight flush, four of a kind, etc. respectively.
Then runs backwards from highest ranking hand to lowest. If one of these methods returns true, then you can easily pick off the best hand that satisfies that condition. For example on
2h Kh Qh Jh Th 9h 6c
ContainsStraightFlush
would return true, and then you can pick off 9h Th Jh Qh Kh
as the best hand.
Start by sorting the cards, it will make doing your search for the best hand that much easier, then you just have to compare adjacent elements for multiples of the same number, or straights. then you just have a special case to look for a flush
The easiest way to do it is make every collection of 5 cards possible and grab the hand value. Remember the best hand. There are only 21 combinations for the 7 card situation, so it's not good in terms of optimality, but it's not terrible either unless you are using this for research.
foreach (possible 5 card combination in allCards)
bestHand = Max(bestHand, GetValue(possible));
Alternatively you could create an array that has 1 entry for each card, and each index is a pointer to new array which has all 2 card combinations, and each index in that is an array for all 3 card combinations, etc. If you work it out with all suit and rank abstractions possible, the total size of the data structure is about 128 MB in memory. There is a reference implementation in c++ on the 2+2 forums.
Don't do it like this, it is awfully slow and actually rather cumbersome to write (the logic is quite hairy). Also, for Monte Carlo simulations where you'll need to run hundred of millions of hands, such an approach simply cannot stand.
See this link for a survey of available techniques. Actually, using table-based comparison algorithms is much simpler to code than using a truckload of if statements.
Most of the routines presented in the above article are available in already-bundled C# libraries that you can plug your code into.
[The first high-performance original idea is there, and uses lookup tables, perfect hashes and a nice trick of multiplying prime numbers to evaluate a hand at a glance.]
create an array of cards, and add the first 5 cards. Then, foreach additional card, find the lowest in the card hand, and see if the extra card is larger, if so, switch them. Keeping in mind that you need to find pairs, straights, and full houses and such
精彩评论