A few weeks ago I read the article “Are poker ‘bots’ raking online pots?” on
MSNBC’s website. Being an avid poker player/enthusiast I started toying with
the idea of writing a Texas Hold’em bot just for the fun of it (ya, I know,
geek). Although it seemed like a great idea at the time my enthusiasm for
actually writing it wasn’t too high. Then I came across the article “Poker
Bots: How Bad of a Problem are they?” that stated that “many computer
programmers are going to try and fail in developing their poker bots.” Sadly, I
took this as a personal affront and decided to write the bot.
However, with a slight twist. I am not trying to have my bot play in any online
games or anything. I just want to see how it will do against bots created by
other programmers. After enlisting several of my co-workers to write bots I
started looking for other people to enter and thought that Code Project was a
great place to start. So, I am posting this article in an attempt to get some
of you programmers out there involved in our little tournament.
In this article I will go over the PlayingCardLibrary that I built to implement
the cards and the evaluations of hands. As well as, the requirements for anyone
wanting to submit a bot into the tournament. Not wanting to re-invent the wheel
I decided to look around and see what was already out there. During my browsing
around I found several libraries that were used to evaluate hands and implement
the cards but I didn’t care for them. They often seemed long and confusing, so
I decided to write my own.
The PlayingCardLibrary is a library that implements your standard 52 card deck.
Ace of Spades, down to the 2 of clubs. It has 4 classes of relevance.
Understanding the Library
Card.cs,of course, represents the basic card in a 52 card deck. It
has a member (rank) and a suit with properties to access that information. Card
also has a public method that can be used to get the image of the card in JPG
public Image CardImage()
return (new CardImages.ImageRetrival()).GetImage(cardValue);
IComparable which allows the cards
to be sorted in two ways. If
sortWithSuit is set to true, then the
sorting will be done with regards to suit first, then rank, meaning that if you
placed all the cards in an
ArrayList and called its sort method
the cards would be arranged exactly like a new deck of cards: Ace of Spades
down to the Two of Spades, then hearts, diamonds and clubs. If
false, then the cards are sorted Ace’s, King’s, Queen’s, Jack’s, …, 3’s,
Deck.cs is your basic 52 card deck. It has three public methods of
interest, Shuffle, which randomizes the cards in the deck. Resets the
to zero so new cards are dealt from the top of the deck (figuratively).
public void Shuffle()
deckIndex = 0;
int temp = 0;
for(int i = 0; i < cards.Length; i++)
temp = random.Next(0,cards.Length);
card = cards[temp];
cards[temp] = cards[i];
cards[i] = card;
DealNext() methods work in
HasNext() indicates if there is another card that can
be dealt and
DealNext() deals that card. Calling
HasNext() can lead to an
which is changed into a
PokerGames5Cards.cs is where things get a little more interesting.
After searching for an existing library that could evaluate a set of cards to
determine the best possible 5 card (Hand) set, I found that most of the
existing code was more complicated then it needed to be, often consisting of
several hundred lines of code that was confusing to use. After a few hours of
searching and examining existing packages I decided to write this library.
Central to this library is the evaluation method.
has only one public method:
Evaluate, it takes a
array of 5 or more cards and an
object, it returns the best 5 card
hand. The basic idea behind Evaluate is that it makes every possible 5 card
combination and then sorts them based on the relative strength of the hand.
public Hand Evaluate(Card cards, object player)
if(cards.Length < 5)
throw new ArgumentException("Not enough Cards to perform evaluation");
ArrayList combinations = new ArrayList();
int len = cards.Length;
for(int i = 0; i < len - 4; i++)
for(int j = i+1; j < len - 3; j++)
for(int k = j+1; k < len - 2; k++)
for(int r = k+1; r < len - 1; r++)
for(int s = r+1; s < len; s++)
Hand h = new Hand(player);
The code needed to determine if a hand falls with in a certain category (flush,
straight, …) is fairly straight forward and I’ll leave it up to the readers to
examine the code directly. The interesting part is how we evaluate each hand.
Because poker hands neatly partition themselves into categories and each
category can be further partitioned into subcategories, I decided to map all
possible hands into the set of integers. With this accomplished, any hand can
be quickly and easily compared to any other hand, without having to go into all
the checks (to see if they are both 2 pairs, then checking the pairs, then
checking the kickers if needed) so prominent in other packages.
I start by evaluating each hand to determine what major category it falls into
(Flush, straight, …), then I reorder the cards with the strongest cards
relative to the major category in the front. (The reordering isn’t really
necessary but it makes it easier to put on screen if they are already in
Example one: (AH) = (rank, suit) = Ace of Hearts
3H, 5H, JH, 8H 2H falls into the major category for flushes. The cards are then
reordered to JH, 8H, 5H, 3H, 2H and mapped into a 32 bit integer using the
following private method.
private int SetHandValue()
int handValue = 0;
handValue = ApplyMask(handValue, (int) type, 20);
handValue = ApplyMask(handValue, (int) cards.GetMember, 16);
handValue = ApplyMask(handValue, (int) cards.GetMember, 12);
handValue = ApplyMask(handValue, (int) cards.GetMember, 8);
handValue = ApplyMask(handValue, (int) cards.GetMember, 4);
handValue = ApplyMask(handValue, (int) cards.GetMember, 0);
private int ApplyMask(int origninal, int value, int shift)
int temp = value << shift;
return origninal | temp;
type is of
private enum Type
HighCard = 0,
Example two:(already reordered)
(Hand 1)8H, 8D, 2H, 2D, KC = 0010 1000 1000 0010 0010 1101
(Hand 2)8S, 8C, 2S, 2C, AC = 0010 1000 1000 0010 0010 1110
now we can see that Hand 2 easily beats Hand 1 simply by checking it numerical
Hand.cs is relatively simple, it is a place to hold the
for each hand, the numerical value of the hand, and implements the
interface so the hands can be compared against other hands.
In Summary, all of the classes in this library are short and to the point. Hands
are easily partitioned possible into groups and subgroups (including kicker
cards) that can be mapped directly to the set of integers for easy comparison.
BOT CHALLENGE 2K5 !!
Ok, so the fun stuff.... who is programmer enough to compete? On too, THE
PROGRAMMERS CHALLENGE!!! I have written a little Texas Hold’em game. And I’d
like to have as many people as possible submit their idea of a great poker bot.
In January 05 we’ll have a series (around 1000) of tournaments to determine the
winning bot. The reason for having more then one tournament is to give the bots
a chance to learn the moves of the other bots (if desired), rather then to just
rely on the statistics of the current hand, if they want to.
What your bot must do
Please Examine the second zip file. It contains all the files that you need in
order to complete your bot. Of course, you need the card library along with:
HoldemPlayer.cs are to abstract
classes that provide a lot of the basic functionality of the player. Your bot
HoldemPlayer.cs, inside the holdem player you have the
Card cards contains your hole cards, you
to determine if you are the dealer or one of blinds. Your inheriting class must
provide concrete implementation for the abstract methods in HoldemPlayer and
AbstractPlayer. That is, you must provide the functionality for the following
public override HoldemActionEvent
EvaluateCurrentAction you need to make some kind of move, you are passed the
current game state, which gives you
PlayersChipCount (returns the
players chip count),
AmountNeededToCall (returns the amounted
needed to call),
GetPlayerList (returns a list of the active
GetCommunityCards (returns the table cards),
(tells you what the current bigBlind is),
GetPotSize (tells you
the current size of the pot) and
GetLastAction (returns the last
action that was performed)
public override void HoldemActionUpdate(HoldemActionEvent action)
ActionUpdate is a curtsy method that informs all the plays of
moves that are made, as they are made, including your moves. They can be used
to track the game. Then when you get the game state in
you can verify your internal tracking.
public override void HoldemActionUpdate(HoldemActionEvent action)
HoldemActionUpdate gives you access to the event of the player. Specifically,
the event action and
Amount returns the amount associated with
that action. where
Actions is the following enumeration.
public enum Actions
FOLD = 1,
OK, so, if you up for the action, email your bots (as text only - no
attachments) to the BotChallenge2k5@hotmail.com with the following subject
line: "BOT CHALLENGE 2K5 !!"
and the winner will be posted after the tournaments have been run... Good
programming and Good luck. These emails will be read in as text and placed into
a single file named after whatever you call your class that extend
so please be sure that all of the classes that you need are all working
properly... No extra text, if it doesn't compile, its deleted.