def calculate_hand_strength(current_hole_cards, board_cards, full_deck):
        """
        Implemented as described in the page 21 of the thesis in: http://poker.cs.ualberta.ca/publications/davidson.msc.pdf
        """
        our_cards = current_hole_cards + board_cards
        our_cards_set = frozenset(our_cards)
        if len(our_cards_set) == 2:
            return STRENGTH_TABLE_FOR_2_CARDS[our_cards_set]
        else:
            pokereval = PokerEval()
            ahead = 0.0
            tied = 0.0
            behind = 0.0
            our_rank = pokereval.evaln(our_cards)
            # considers all two card combinations of the remaining cards

            deck = list(full_deck)
            for card in our_cards:
                if card not in deck:
                    print "Warning! Card not in deck: "+str(card)+", current_hole_cards: "+str(current_hole_cards)+", board_cards: "+str(board_cards)
                deck.remove(card)
            opponent_cards_combinations = itertools.combinations(deck, 2)

            for opponent_card1, opponent_card2 in opponent_cards_combinations:
                opponent_rank = pokereval.evaln([opponent_card1] + [opponent_card2] + board_cards)
                if our_rank > opponent_rank:
                    ahead += 1.0
                elif our_rank == opponent_rank:
                    tied += 1.0
                else:
                    behind += 1.0
            hand_strength = (ahead + tied/2.0) / (ahead + tied + behind)
            return hand_strength
Пример #2
0
    def __init__(self, protocol, avatar, table_info):
        self.protocol = protocol
        self.id = table_info.get('id', 0)
        self.seat = table_info.get('player_seated', -1)
        self.seats = [0] * table_info.get('seats', 10)
        if self.seat != -1:
            self.seats[self.seat] = avatar.serial
            assert avatar.seat == self.seat, "as %s, ss %s" % (avatar.seat,
                                                               self.seat)
        self.name = table_info.get('name', 'unnamed')
        self.betting_structure = table_info['betting_structure']
        blinds, buy_ins, limit = table_info['betting_structure'].split('_')
        min_buy_in, max_buy_in = buy_ins.split('-')
        small, big = blinds.split('-')

        self.max_buy_in = int(max_buy_in) * 100
        self.min_buy_in = int(min_buy_in) * 100
        self.big_blind = int(big) * 100
        self.small_blind = int(small) * 100

        self.players = {avatar.serial: avatar}
        self.avatar = avatar
        self._serial_and_game_id = dict(serial=avatar.serial, game_id=self.id)
        self._eval = PokerEval()
        self.reset()
        self._game_state = GAME_STATE_NULL
Пример #3
0
 def getValue(self, card):
     value = None
     if type(card) is str:
         poker_eval = PokerEval()
         try: value = poker_eval.string2card(card)
         except RuntimeError: raise UserWarning, "Invalid card %s" %(card)
     else:
         if card != PokerCards.NOCARD:
             value = card & PokerCards.VALUE_CARD_MASK
             if (value < 0) or (value >= PokerCards.NB_CARD):
                 raise UserWarning, "Invalid card %s" %(card)
         value = card
     return value
Пример #4
0
 def getValue(self, card):
     value = None
     if type(card) is str:
         poker_eval = PokerEval()
         try:
             value = poker_eval.string2card(card)
         except RuntimeError:
             raise UserWarning, "Invalid card %s" % (card)
     else:
         if card != PokerCards.NOCARD:
             value = card & PokerCards.VALUE_CARD_MASK
             if (value < 0) or (value >= PokerCards.NB_CARD):
                 raise UserWarning, "Invalid card %s" % (card)
         value = card
     return value
Пример #5
0
    def __init__(self, protocol, avatar, table_info):
        self.protocol = protocol
        self.id = table_info.get('id', 0)
        self.seat = table_info.get('player_seated', -1)
        self.seats = [0] * table_info.get('seats', 10)
        if self.seat != -1:
            self.seats[self.seat] = avatar.serial
            assert avatar.seat == self.seat, "as %s, ss %s" % (avatar.seat, self.seat)
        self.name = table_info.get('name', 'unnamed')
        self.betting_structure =  table_info['betting_structure']
        blinds, buy_ins, limit = table_info['betting_structure'].split('_')
        min_buy_in, max_buy_in = buy_ins.split('-')
        small, big = blinds.split('-')

        self.max_buy_in = int(max_buy_in)*100
        self.min_buy_in = int(min_buy_in)*100
        self.big_blind = int(big)*100
        self.small_blind = int(small)*100

        self.players = {avatar.serial: avatar}
        self.avatar = avatar
        self._serial_and_game_id = dict(serial=avatar.serial, game_id=self.id)
        self._eval = PokerEval()
        self.reset()
        self._game_state = GAME_STATE_NULL
Пример #6
0
    def __init__(self):
        """This is a very simple player that demonstrates the API and is a good
        template for getting started
        """
        # my name
        self.name = "theBostonDerby"

        self.reset(False,[])
        # game state variables -- these are updated by the engine which
        # own internal representation. so if you modify them, they'll just
        # be reset. we recommend leaving their init as is
        self.hand = None
        self.stack = None
        self.pip = None
        self.button = None
        self.opponent = None
        self.bb = None
        self.sb = None
        self.hands_played = None
        self.last_hand = 0
        self.board = None
        self.legal = None
        self.actions = None
        self.last = None
        self.pot = None
        self.ev_calc = PokerEval()
        self.ev = 0
        self.bound = 0
        self.bot = BaseBot()
        self.LOW = .02
        self.MID = .08
        self.HIGH = .15
Пример #7
0
 def __init__(self):
     self.hand_groups = {
         "A":["AA", "AKs", "KK"],
         "B":["AK", "QQ"],
         "C":["JJ", "TT"],
         "D":["AQs", "AQ", "AJs", "99", "88"],
         "E":["AJ","ATs","KQs", "77","66","55"],
         "F":["AT","KQ","KJs","QJs","44","33","22"],
         "G":["A9s","A8s","A7s","A6s","A5s","A4s","A3s","A2s","KTs","QTs","JTs","J9s","T9s","98s"],
         "H":["KJ","KT","QJ","J8s","T8s","87s","76s"]
     }
     self.hand_values = {"A":13,"K":12,"Q":11,"J":10, "T":9,"9":8,"8":7,"7":6,"6":5,"5":4,"4":3,"3":2,"2":1}
     self.odds_map = {
         "flop":{1:0.045,2:0.088,3:0.13,4:0.172,5:0.212,6:0.252,7:0.29,8:0.327,9:0.364,10:0.399,11:0.433,12:0.467,13:0.499,14:0.53,15:0.561,16:0.59,17:0.618},
         "turn":{1:0.023,2:0.045,3:0.68,4:0.091,5:0.114,6:0.136,7:0.159,8:0.182,9:0.205,10:0.227,11:0.25,12:0.273,13:0.295,14:0.318,15:0.341,16:0.364,17:0.386}
     }
     self.eval = PokerEval()
Пример #8
0
    def __init__(self, pname):
        self.history = [{}, {}, {}, {}]
        for a in range(4):  # [BET,CALL,CHECK,RAISE]:
            for s in range(4):
                self.history[s][a] = []

        self.pname = pname
        self.pokereval = PokerEval()
        self.showStats = {}
Пример #9
0
 def __init__(self, had_values, hand, board):
     self.eval = PokerEval()
     self.hand_values = {
         "A": 13,
         "K": 12,
         "Q": 11,
         "J": 10,
         "T": 9,
         "9": 8,
         "8": 7,
         "7": 6,
         "6": 5,
         "5": 4,
         "4": 3,
         "3": 2,
         "2": 1
     }
     self.hand = hand
     self.board = board
Пример #10
0
    def calculate_hand_strength(current_hole_cards, board_cards, full_deck):
        """
        Implemented as described in the page 21 of the thesis in: http://poker.cs.ualberta.ca/publications/davidson.msc.pdf
        """
        our_cards = current_hole_cards + board_cards
        our_cards_set = frozenset(our_cards)
        if len(our_cards_set) == 2:
            return STRENGTH_TABLE_FOR_2_CARDS[our_cards_set]
        else:
            pokereval = PokerEval()
            ahead = 0.0
            tied = 0.0
            behind = 0.0
            our_rank = pokereval.evaln(our_cards)
            # considers all two card combinations of the remaining cards

            deck = list(full_deck)
            for card in our_cards:
                if card not in deck:
                    print "Warning! Card not in deck: " + str(
                        card) + ", current_hole_cards: " + str(
                            current_hole_cards) + ", board_cards: " + str(
                                board_cards)
                deck.remove(card)
            opponent_cards_combinations = itertools.combinations(deck, 2)

            for opponent_card1, opponent_card2 in opponent_cards_combinations:
                opponent_rank = pokereval.evaln([opponent_card1] +
                                                [opponent_card2] + board_cards)
                if our_rank > opponent_rank:
                    ahead += 1.0
                elif our_rank == opponent_rank:
                    tied += 1.0
                else:
                    behind += 1.0
            hand_strength = (ahead + tied / 2.0) / (ahead + tied + behind)
            return hand_strength
Пример #11
0
class EvalDraws:
    def __init__(self, had_values, hand, board):
        self.eval = PokerEval()
        self.hand_values = {"A":13,"K":12,"Q":11,"J":10, "T":9,"9":8,"8":7,"7":6,"6":5,"5":4,"4":3,"3":2,"2":1}
        self.hand = hand
        self.board = board
    def convertHandValue(self, cards):
        deck = []
        for card in cards:
            deck.append(self.hand_values[card[0]])
        return sorted(deck)
    def lookForDraws(self):
        h = self.hand.split(" ")
        b = self.board.split(" ")
        cards = h + b
        has_flush = self.lookForFlushDraw(cards)
        if has_flush != False:
            return has_flush
        has_straight = self.lookForStraightDraw(cards, False)
        if has_straight != False:
            return has_straight
        return False
    def lookForFlushDraw(self, cards):
        suits = {"s":0,"c":0,"h":0,"d":0}
        for card in cards:
            if card != "__":
                suits[card[1]] += 1
        for suit in suits:
            if suits[suit] > 3:
                has_straight = self.lookForStraightDraw(cards, True)
                if has_straight != False:
                    return "%s%s" %(has_straight, "Flush")
                return "FlushDraw"
        return False
    def lookForStraightDraw(self, cards, flush = False):
        if flush != False:
            deck = sorted(self.eval.string2card(cards))
        else:
            deck = self.convertHandValue(cards)
        for k,v in enumerate(deck):
            max_len = 3
            if (k + max_len) < len(deck) :
                my_range = range(v, (v + (max_len + 1)))
                if deck[k+max_len] == my_range[len(my_range) - 1]:
                    return "OpenEndedStraight"
                elif deck[k+max_len] == ((my_range[len(my_range) - 1] +1) or (my_range[len(my_range) - 1] - 1)):
                    return "GutShotStraight"
        return False
Пример #12
0
class EvalDraws:
    def __init__(self, had_values, hand, board):
        self.eval = PokerEval()
        self.hand_values = {"A":13,"K":12,"Q":11,"J":10, "T":9,"9":8,"8":7,"7":6,"6":5,"5":4,"4":3,"3":2,"2":1}
        self.hand = hand
        self.board = board
    def convertHandValue(self, cards):
        deck = []
        for card in cards:
            deck.append(self.hand_values[card[0]])
        return sorted(deck)
    def lookForDraws(self):
        h = self.hand.split(" ")
        b = self.board.split(" ")
        cards = h + b
        has_flush = self.lookForFlushDraw(cards)
        if has_flush != False:
            return has_flush
        has_straight = self.lookForStraightDraw(cards, False)
        if has_straight != False:
            return has_straight
        return False
    def lookForFlushDraw(self, cards):
        suits = {"s":0,"c":0,"h":0,"d":0}
        for card in cards:
            if card != "__":
                suits[card[1]] += 1
        for suit in suits:
            if suits[suit] > 3:
                has_straight = self.lookForStraightDraw(cards, True)
                if has_straight != False:
                    return "%s%s" %(has_straight, "Flush")
                return "FlushDraw"
        return False
    def lookForStraightDraw(self, cards, flush = False):
        if flush != False:
            deck = sorted(self.eval.string2card(cards))
        else:
            deck = self.convertHandValue(cards)
        for k,v in enumerate(deck):
            max_len = 3
            if (k + max_len) < len(deck) :
                my_range = range(v, (v + (max_len + 1)))
                if deck[k+max_len] == my_range[len(my_range) - 1]:
                    return "OpenEndedStraight"
                elif deck[k+max_len] == ((my_range[len(my_range) - 1] +1) or (my_range[len(my_range) - 1] - 1)):
                    return "GutShotStraight"
        return False
Пример #13
0
 def __init__(self):
     self.hand_groups = {
         "A":["AA", "AKs", "KK"],
         "B":["AK", "QQ"],
         "C":["JJ", "TT"],
         "D":["AQs", "AQ", "AJs", "99", "88"],
         "E":["AJ","ATs","KQs", "77","66","55"],
         "F":["AT","KQ","KJs","QJs","44","33","22"],
         "G":["A9s","A8s","A7s","A6s","A5s","A4s","A3s","A2s","KTs","QTs","JTs","J9s","T9s","98s"],
         "H":["KJ","KT","QJ","J8s","T8s","87s","76s"]
     }
     self.hand_values = {"A":13,"K":12,"Q":11,"J":10, "T":9,"9":8,"8":7,"7":6,"6":5,"5":4,"4":3,"3":2,"2":1}
     self.odds_map = {
         "flop":{1:0.045,2:0.088,3:0.13,4:0.172,5:0.212,6:0.252,7:0.29,8:0.327,9:0.364,10:0.399,11:0.433,12:0.467,13:0.499,14:0.53,15:0.561,16:0.59,17:0.618},
         "turn":{1:0.023,2:0.045,3:0.68,4:0.091,5:0.114,6:0.136,7:0.159,8:0.182,9:0.205,10:0.227,11:0.25,12:0.273,13:0.295,14:0.318,15:0.341,16:0.364,17:0.386}
     }
     self.eval = PokerEval()
Пример #14
0
 def __init__(self):
     """This is a very simple player that demonstrates the API and is a good
     template for getting started
     """
     # my name
     self.name = "theBostonDerby"
     self.restart()
     # game state variables -- these are updated by the engine which
     # own internal representation. so if you modify them, they'll just
     # be reset. we recommend leaving their init as is
     self.hand = None
     self.stack = None
     self.pip = None
     self.button = None
     self.opponent = None
     self.bb = None
     self.sb = None
     self.hands_played = None
     self.opp_last_stack = self.stack
     self.board = None
     self.legal = None
     self.actions = None
     self.last = None
     self.pot = None
     self.ev_calc = PokerEval()
     self.ev = 0
     self.bot = None
     self.unlimited = True
     self.low_chip_bot = None
     self.high_chip_bot = None
     self.bot_to_use = None
     self.last_name = ""
     self.last_hand = 0
     self.my_stack = 400
     self.opp_stack = 400
     if hasattr(self,"bots"):
         for b in self.bots:
             b.losses = 0
             b.games_played = 0
         self.bot = self.bots[0]
         self.index = 0
     else:
         self.bots = None
Пример #15
0
    def GET(self):
        input = web.input()
        web.header("Content-Type", "text/plain")
        defaultParams = {
            "game": "holdem",
            "pockets": [],
            "board": [],
            "dead": [],
            "iterations": 10000
        }
        kwargs = defaultParams
        jsonp = None
        for key in input:
            value = input[key]
            if key == "jsoncallback":
                jsonp = value
            elif key in ["game", "pockets", "board", "dead", "iterations"]:
                kwargs[key] = json.read(value)

        cards = []
        for pocket in kwargs["pockets"]:
            cards.extend(pocket)
        cards.extend(kwargs["board"])
        cards.extend(kwargs["dead"])
        duplicate = set(
            filter(lambda card: (card != "__" and cards.count(card) > 1),
                   cards))
        if len(duplicate) > 0:
            poker_eval_result = {
                "error": "duplicate cards: %s" % string.join(duplicate)
            }
        else:
            params = apply_game_params(**kwargs)
            try:
                poker_eval_result = PokerEval().poker_eval(**params)
            except Exception, e:
                poker_eval_result = {"error": str(e)}
Пример #16
0
import eval7
# https://pypi.org/project/eval7/
from pprint import pprint
import sys
import datetime

sys.path.insert(0, ".")
sys.path.insert(0, ".libs")
from pokereval import PokerEval
from tqdm import tqdm
import traceback
from operator import add

pokereval = PokerEval()
'''
 full flop: 52*51*50/6 = 22,100
 rainbow : 2197(given three color) * 4 (C1,4) = 8788  39%
 TwoColor: 2*(13*12/2)*13* 6 (C2,4) = 12168  55%
 OneColor: 13*12*11/6 * 4 (C1,4) = 1144 5.2%

'''

# hr1 3-bet for value
# hr2 3-bet for lesser value
# hr3 for call

hr1 = eval7.HandRange("TT+, AQ+, KQ+")  # 78 combo
hr2 = eval7.HandRange("77+, A9+, KT+, QT+, JT, T9s, 98s, 87s, 76s, 65s")
hr3 = eval7.HandRange(
    "22+, A7o+, KT+, QT+, JT, T9, 98s, 87s, 76s, 65s, A2s+, K9s, K8s, Q9s, Q8s, \
64s, 75s, 86s, 97s, T8s, J9s")
Пример #17
0
class Strategy:
    def __init__(self):
        self.pokereval = PokerEval()
        self.handRank = None

    def evaluateOdds(self, game):
        self.evaluatePocketCards3(game)
        self.evalHand(game)
        #raise NotImplementedError("evaluateOdds not implemented in subclass")

    def getMove(self, game):
        raise NotImplementedError("getMove not implemented in subclass")

    def evaluatePocketCards2(self, game):
        return TwoPocketLookup.evalPocket(game.holeCard1, game.holeCard2)

    def evaluatePocketCards3(self, game):
        return ThreePocketLookup.evalPocket(game.holeCard1, game.holeCard2)

    def evalHand(self, game, oppEvs = {}):
        hand = [game.holeCard1.stringValue, game.holeCard2.stringValue]
        if game.street==PREFLOP:
            if game.activePlayers == 2:
                ev = self.evaluatePocketCards2(game)
                print "TWO PLAYER UNKNOWN OPP EV: ", ev
                #determine which player is still in
                if game.leftOpp.active == 1:
                    p = game.leftOpp
                else:
                    p = game.rightOpp
                #get their range of hands
                if p.name in oppEvs.keys():
                    pEV = oppEvs[p.name]
                    if pEV[0] != -1:
                        p.handRange = reduce(lambda x,y:x+y, TwoPocketLookup.lookupvalue[max([int(pEV[0]-pEV[1]),0]):min([int(pEV[0]+pEV[1]+1),1000])])
                        if len(p.handRange) == 0:
                            p.handRange = [(255,255)]
                        wins = 0
                        iters = ITERATIONS/len(p.handRange)
                        num_hands = 0
                        for h in p.handRange:
                            ev = self.pokereval.poker_eval(game="holdem",pockets=[hand,list(h)],dead=[],board=game.boardCards,iterations=iters)
                            wins += ev['eval'][0]['winhi']+ev['eval'][0]['tiehi']/2.0
                            num_hands+=1
                        ev = 1000 * wins/float(num_hands*iters)
                        print "TWO PLAYER EDUCATED EV:", ev

            else: #3 active players
                ev = self.evaluatePocketCards3(game)
                print "THREE PLAYER UNKNOWN OPP EV: ", ev
                game.leftOpp.handRange = [(255,255)]
                game.rightOpp.handRange = [(255,255)]
                if game.leftOpp.name in oppEvs.keys():
                    pEV = oppEvs[game.leftOpp.name]
                    if pEV[0] != -1:
                        game.leftOpp.handRange = reduce(lambda x,y:x+y, ThreePocketLookup.lookupvalue[max([int(pEV[0]-pEV[1]),0]):min([int(pEV[0]+pEV[1]+1),1000])])
                if game.rightOpp.name in oppEvs.keys():
                    pEV = oppEvs[game.rightOpp.name]
                    if pEV[0] != -1:
                        game.rightOpp.handRange = reduce(lambda x,y:x+y, ThreePocketLookup.lookupvalue[max([int(pEV[0]-pEV[1]),0]):min([int(pEV[0]+pEV[1]+1),1000])])
                if game.leftOpp.handRange !=[(255,255)] or game.rightOpp.handRange !=[(255,255)]:
                    wins = 0
                    samples = 3000
                    num_hands = 0
                    iters  = ITERATIONS/samples
                    for i in range(samples):
                        p1 = list(random.choice(game.leftOpp.handRange))
                        p2 = list(random.choice(game.rightOpp.handRange))
                        pockets = [hand,p1,p2]
                        ev = self.pokereval.poker_eval(game="holdem",pockets=pockets,dead=[],board=game.boardCards,iterations=iters)
                        wins += ev['eval'][0]['winhi'] + ev['eval'][0]['tiehi']/2.0
                        num_hands += 1
                    ev = 1000 * wins/float(num_hands*iters)
                    print "THREE PLAYER EDUCATED EV: ", ev

        else: #post-flop
            if game.activePlayers == 3:
#                wins = 0
#                wins1 = 0
#                wins2 = 0
#                samples = 3000
#                num_hands = 0
#                num_hands1 = 0
#                num_hands2 = 0
#                iters = ITERATIONS/samples
#                for i in range(samples):
#                    #get random pockets from both players
#                    p1 = list(game.leftOpp.handRange[random.randrange(len(game.leftOpp.handRange))])
#                    p2 = list(game.rightOpp.handRange[random.randrange(len(game.rightOpp.handRange))])
#                    pockets = [hand,p1,p2]
#                    ev = self.pokereval.poker_eval(game="holdem",pockets=pockets,dead=[],board=game.boardCards,iterations=iters)
#                    tempWins1 = ev['eval'][1]['winhi'] + ev['eval'][1]['tiehi']/2.0
#                    tempWins2 = ev['eval'][2]['winhi'] + ev['eval'][2]['tiehi']/2.0
#                    tempEV1 = 1000*tempWins1/iters
#                    tempEV2 = 1000*tempWins2/iters
#                    #check if opponent calculated evs are within their predicted evs by the archive
#                    if game.leftOpp.name in oppEvs.keys():
#                        if tempEV1 > (oppEvs[game.leftOpp.name][0] - oppEvs[game.leftOpp.name][1]) and tempEV1 < (oppEvs[game.leftOpp.name][0] +  oppEvs[game.leftOpp.name][1]):
#                            wins1 += tempWins1
#                            num_hands1 += 1
#                    else:
#                        wins1 += tempWins1
#                        num_hands1 += 1
#                    if game.rightOpp.name in oppEvs.keys():
#                        if tempEV2 > (oppEvs[game.rightOpp.name][0] - oppEvs[game.rightOpp.name][1]) and tempEV2 < (oppEvs[game.rightOpp.name][0] +  oppEvs[game.rightOpp.name][1]):
#                            wins2 += tempWins2
#                            num_hands2 += 1
#                    else:
#                        wins2 += tempWins2
#                        num_hands2 += 1
#                    wins += ev['eval'][0]['winhi'] + ev['eval'][0]['tiehi']/2.0
#                    num_hands += 1
#                ev = 1000*wins/float(num_hands*iters)
#                if num_hands1 > 0:
#                    ev1 = 1000*wins1/float(num_hands1*iters)
#                else:
#                    ev1 = -1
#                if num_hands2 >0:
#                    ev2 = 1000*wins2/float(num_hands2*iters)
#                else:
#                    ev2 = -1
#
#                ###unused except for printing
#                naiveEV = self.pokereval.poker_eval(game="holdem",pockets=[hand,[255,255],[255,255]],dead=[],board=game.boardCards,iterations = ITERATIONS)
#                naiveEV = 1000*(naiveEV['eval'][0]['winhi'] + naiveEV['eval'][0]['tiehi']/2.0)/float(ITERATIONS)
#                print "OPPEV KEYS:", oppEvs.keys(), "left:", game.leftOpp.name, "right", game.rightOpp.name
#                if game.leftOpp.name in oppEvs.keys():
#                    LEV = oppEvs[game.leftOpp.name]
#                else:
#                    LEV = -1
#                if game.rightOpp.name in oppEvs.keys():
#                    REV = oppEvs[game.rightOpp.name]
#                else:
#                    REV = -1
#                ###
#
#
#                print "THREE PLAYERS:"
#                print "My naive ev:", naiveEV, " educated ev:", ev
#                print game.leftOpp.name, " ev:", LEV, " educated ev:", ev1
#                print game.rightOpp.name, " ev:", REV, " educated ev:", ev2


                pockets = [hand,[255,255],[255,255]]
            elif game.activePlayers == 2:
#                if game.leftOpp.active == 1:
#                    p = game.leftOpp
#                else:
#                    p = game.rightOpp
#
##                if p.handRange != [(255,255)]:
#                    wins = 0
#                    wins1 = 0
#                    samples = 1000
#                    num_hands = 0
#                    num_hands1 = 0
#                    iters = ITERATIONS/samples
#                    for i in range(samples):
#                        if len(p.handRange)>1:
#                            p1 = list(p.handRange[random.randrange(len(p.handRange))])
#                            pockets = [[255,255],p1]
#                            ev = self.pokereval.poker_eval(game="holdem",pockets=pockets,dead=[],board=game.boardCards,iterations=iters)
#                            tempWins1 = ev['eval'][1]['winhi'] + ev['eval'][1]['tiehi']/2.0
#                            tempEV1 = 1000 * tempWins1/float(iters)
#                            #check if those possible cards in hand range give an EV that is in range we expect from history
#                            if p.name in oppEvs.keys():
#                                if oppEvs[p.name][0] != -1:
#                                    if tempEV1 > (oppEvs[p.name][0] - oppEvs[p.name][1]) and tempEV1 < (oppEvs[p.name][0] +  oppEvs[p.name][1]):
#                                        wins1 += tempWins1
#                                        num_hands1 += 1
#                            else:
#                                wins1 += tempWins1
#                                num_hands1 += 1
#                            print "REMOVING ELEMNT", p1
#                            p.handRange.remove((p1[0],p1[1]))
#                            #update our EV
#                            pockets = [hand, p1]
#                            ev = self.pokereval.poker_eval(game="holdem",pockets=pockets,dead=[],board=game.boardCards,iterations=iters)
#                            wins += ev['eval'][0]['winhi'] + ev['eval'][0]['tiehi']/2.0
#                            num_hands += 1
#                    ev = 1000*wins/float(num_hands*iters)
#                    if num_hands1 > 0:
#                        ev1 = 1000*wins1/float(num_hands1*iters)
#                    else:
#                        ev1 = -1
##
#                    ###only used in printing
#                    naiveEV = self.pokereval.poker_eval(game="holdem",pockets=[hand,[255,255]],dead=[],board=game.boardCards,iterations = ITERATIONS)
#                    naiveEV = 1000*(naiveEV['eval'][0]['winhi'] + naiveEV['eval'][0]['tiehi']/2.0)/float(ITERATIONS)
#                    if p.name in oppEvs.keys():
#                        PEV = oppEvs[p.name]
#                    else:
#                        PEV = -1
#
#                    print "TWO PLAYERS:"
#                    print "my naive ev:", naiveEV, " educated ev:", ev
#                    print p.name, " ev:", PEV, " educated ev:", ev1
#                    print "gameboard", game.boardCards
#
#                else:
                pockets = [hand,[255,255]]
            else:
                # shouldn't get here, but just in case
                print "Only 1 active player! EV is 1"
                return 1000

            ev = self.pokereval.poker_eval(game="holdem",
                                           pockets = pockets,
                                           dead=[],
                                           board=game.boardCards,
                                           iterations = ITERATIONS)['eval'][0]['ev']

#        print "HAND", hand, "BOARD", board, "EV", ev

        return ev

    #Bet or raise the minimum amount, or times some multiplier
    # If min raise amount is to raise to 4, multiplier of 3 says to raise to
    # 3*4=12
    def pushMin(self, game, m=1):
        move = Move(CALL)
        for la in game.legalActions:
            if la[0] == "BET":
                return Move(BET, min(game.me.getAllIn(),int(la[1])*m))
            if la[0] == "RAISE":
                return Move(RAISE, min(game.me.getAllIn(),int(la[1])*m))

##        print "PUSH MIN MOVE:", move
        return move

    ##If can check, then check.  Otherwise call up to m
    def maxRisk(self, game, m):
        if "CHECK" in [la[0] for la in game.legalActions]:
            return Move(CHECK)
        if game.lastBet <= m:
            return Move(CALL)
        return Move(FOLD)

    def betPot(self, game, m):
        move = Move(CALL)
        amt = min(game.me.getAllIn(),m*(game.pot + game.leftOpp.pip + game.rightOpp.pip + game.me.pip))
        for la in game.legalActions:
            if la[0] == "BET":
                return Move(BET, amt)
            if la[0] == "RAISE":
                return Move(RAISE, amt)

##        print "PUSH MIN MOVE:", move
        return move
    def raiseBet(self, game, m):
        move = Move(CALL)
        highpip2 = sorted([game.me.pip, game.leftOpp.pip, game.rightOpp.pip])[1]
        amt = 3*(game.lastBet-highpip2)
        amt = max(game.pot, amt)
        amt = min(game.me.getAllIn(),m*amt)
        for la in game.legalActions:
            if la[0] == "RAISE":
                return Move(RAISE, amt)
        return move
Пример #18
0
 def __init__(self):
     self.pokereval = PokerEval()
     self.handRank = None
Пример #19
0
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301, USA.
#
# http://gna.org/support/?1823
#
import sys

sys.path.insert(0, ".")
sys.path.insert(0, ".libs")

from pokereval import PokerEval

pokereval = PokerEval()

result = pokereval.poker_eval(game="holdem",
                              fill_pockets=1,
                              pockets=[["As", "3s"], ["__", "__"]],
                              dead=[],
                              board=["Ad", "Qs", "2c", "Ac", "Kc"])
assert result == {
    'info': (990, 0, 1),
    'eval': [{
        'winlo': 0,
        'tielo': 0,
        'winhi': 877,
        'scoop': 877,
        'loselo': 0,
        'ev': 903,
Пример #20
0
class TheBostonDerby:
    def __init__(self):
        """This is a very simple player that demonstrates the API and is a good
        template for getting started
        """
        # my name
        self.name = "theBostonDerby"
        self.restart()
        # game state variables -- these are updated by the engine which
        # own internal representation. so if you modify them, they'll just
        # be reset. we recommend leaving their init as is
        self.hand = None
        self.stack = None
        self.pip = None
        self.button = None
        self.opponent = None
        self.bb = None
        self.sb = None
        self.hands_played = None
        self.opp_last_stack = self.stack
        self.board = None
        self.legal = None
        self.actions = None
        self.last = None
        self.pot = None
        self.ev_calc = PokerEval()
        self.ev = 0
        self.bot = None
        self.unlimited = True
        self.low_chip_bot = None
        self.high_chip_bot = None
        self.bot_to_use = None
        self.last_name = ""
        self.last_hand = 0
        self.my_stack = 400
        self.opp_stack = 400
        if hasattr(self,"bots"):
            for b in self.bots:
                b.losses = 0
                b.games_played = 0
            self.bot = self.bots[0]
            self.index = 0
        else:
            self.bots = None

    def reset(self, won, last_hand):
        """Reset accepts a boolean indicating whether you won a match and
        provides the last hand if you want to update any statistics from it
        """
        #print "game over", last_hand
        self.calculate_stats(last_hand)
        self.last_hand = 0
        self.my_stack = 400
        self.opp_stack = 400
        if self.bots:
            self.bot.losses += not won
            self.bot.games_played += 1
            #print self.bot.losses
            if (self.bot.games_played < 6 and self.bot.losses > 2) or (self.bot.games_played >= 6 and self.bot.losses/float(self.bot.games_played) > .5):
                self.index += 1
                #print self.index
                if self.index >= len(self.bots):
                    self.index = 0
                    self.bots = sorted(self.bots,key=lambda x:x.losses)
                    #print [(b.name,b.losses) for b in self.bots]
                self.bot = self.bots[self.index]
                #print "using bot", self.bot.name

    def restart(self):
        self.my_stats = {   'hands':0,
                            '^VPIP':[0,0,0,0],
                            'VPIP':[0,0,0,0],  # amount voluntarily placed in pot
                            '^INCR':[0,0,0,0],
                            'INCR':[0,0,0,0],   # frequency of raises
                            '^AF':0,
                            '_AF':0,
                            'AF':0,    # aggression frequency = (bets + raises)/(checks + calls)
                            #pre flop
                            '^ST':0,
                            'ST':0,    # steals = how often he raises when has first action
                            '^LMP':0,
                            'LMP':0,  # how often opponent calls
                            '_3B':0,
                            '^FBB':0,
                            'FBB':0,    # how often, after small blind raises, big blind folds
                            '^3B':0,
                            '3B':0,    # how often, after small blind raises, big blind raises
                            '_4B':0,
                            '^F3B':0,
                            'F3B':0,   # how often, after small blind raises and then big blind raises, small blind folds
                            '^4B':0,
                            '4B':0,    # how often, the small bind raises in above circumstances
                            '_F4B':0,
                            '^F4B':0,
                            'F4B':0,    #how often big blind folds to 4B
                            #flop
                            '_COB':0,
                            '^COB':0,
                            'COB':0,    # continuation bet = how often betting after betting/raising on preflop
                            '_FCOB':0,
                            '^FCOB':0,
                            'FCOB':0,   # how often opp folds to a continuation bet
                            #turn
                            '_2COB':0,
                            '^2COB':0,
                            '2COB':0,   # how often opp cb twice, once on flop and once on turn
                            '_F2COB':0,
                            '^F2COB':0,
                            'F2COB':0,  # how often opp folds to 2nd continuation bet.
                            '_CHBR':[0,0,0,0],
                            '^CHBR':[0,0,0,0],
                            'CHBR':[0,0,0,0],    # how often opp check raises
                            '^HAI':0,
                            'HAI':0,     # percent hands won by going all in
                            '^HPFBB':0,    #number of hands that go to the flop as BB
                            'HPFBB':0,
                            '^HPFSB':0,    #number of hands that go to the flop as SB
                            'HPFSB':0,
                            '^HPT':0,    #number of hands that go to the turn
                            'HPT':0,
                            '^HPR':0,    #number of hands that go to the river
                            'HPR':0
                         }
                     
        self.opp_stats = self.my_stats.copy()
        self.opp_stats['^VPIP'] = [0,0,0,0]
        self.opp_stats['VPIP'] = [0,0,0,0]
        self.opp_stats['^INCR'] = [0,0,0,0]
        self.opp_stats['INCR'] = [0,0,0,0]
        self.opp_stats['_CHBR'] = [0,0,0,0]
        self.opp_stats['^CHBR'] = [0,0,0,0]
        self.opp_stats['CHBR'] = [0,0,0,0]
        self.opp_hand = 100.0
        self.hands_played_against = 0
        self.cory_stats = {'^A':0, 'A':0, '^W':0, 'W':0, '^C':0, 'C':0}

    def card2str(self, c):
        return c.__str__()

    def calculate_ev(self):
        #print self.board
        if not self.board.flop():
            suited = self.hand[0].suit != self.hand[1].suit #0 means suited, 1 means not
            if self.hand[0].rank > self.hand[1].rank:
                card_2,card_1 = self.hand
            else:
                card_1,card_2 = self.hand
            #print "looking up (%d,%d,%d)" % (card_1.rank-2,card_2.rank-card_1.rank,suited)
            ev = 100.0 - lookuphand[card_1.rank-2][card_2.rank-card_1.rank][suited]
        else:
            board = [self.card2str(c) for c in self.board.flop()]
            my_hand = [self.card2str(c) for c in self.hand]
            dead = my_hand
            if self.board.river():
                board += [self.card2str(self.board.turn()), self.card2str(self.board.river())]
                dead += board[:]
            elif self.board.turn():
                board += [self.card2str(self.board.turn()), '__']
                dead += board[:-1]
            else:
                board += ['__','__']
                dead += board[:-2]
            #self.opp_hand == 100.0
            if self.opp_hand == 100.0:
                ev = self.ev_calc.poker_eval(game="holdem",pockets=[[self.card2str(c) for c in self.hand],['__','__']],dead=[],board=board,iterations=1000)
                ev = ev['eval'][0]['ev']/10.0
            else:
                hands = reduce(lambda x,y:x+y, lookupvalue[:int(self.opp_hand*10)])
                wins = 0
                iters = 30
                num_hands = 0
                for hand in hands:
                    if hand[0] in dead or hand[1] in dead: continue
                    ev = self.ev_calc.poker_eval(game="holdem",pockets=[my_hand,list(hand)],dead=[],board=board,iterations=iters)
                    wins += ev['eval'][0]['winhi']+ev['eval'][0]['tiehi']/2.0
                    num_hands += 1
                ev = wins/float(num_hands*iters)
        self.ev = ev/100.0

    def classify(self, act):
        action = None
        if isinstance(act, Post):
            action = POST
        elif isinstance(act, Check): 
            action = CHECK
        elif isinstance(act, Bet):
            action = BET
        elif isinstance(act, Raise): 
            action = RAISE
        elif isinstance(act, Fold): 
            action = FOLD
        elif isinstance(act, Call): 
            action = CALL
        elif isinstance(act, Show):
            action = SHOW
        elif isinstance(act, Deal): 
            action = DEAL
        elif isinstance(act, Won): 
            action = WON
        else :
            if DEBUG: print "umm, unknown action taken!", act
        return action
        
    def calculate_stats(self,last):
        #parse all actions in previous hand into useful information
        if DEBUG: print "calculating stats for hand: ", last
        if len(last) < 3: 
            #print "umm, short hand?!", last
            return
        tallies = {'raises':0, 'bets':0, 'folds':0, 'calls':0, 'checks':0, 'pip':0}
        my_actions = dict(zip(range(4),[tallies.copy() for x in range(4)]))
        opp_actions = dict(zip(range(4),[tallies.copy() for x in range(4)]))
        hand = deque(last[:])
        act = hand.popleft() #first action is always sb posting their blind
        if act[0] == self.name:
            my_actions['position'] = True #position = 1 means sb, 0 means BB
            opp_actions['position'] = False #if i'm not small blind, opp must be
            my_actions[0]['pip'] = act[1].amount
            opp_actions[0]['pip'] = 2 * act[1].amount
        else:
            my_actions['position'] = False #position = 1 means sb, 0 means BB
            opp_actions['position'] = True #if i'm not small blind, opp must be
            opp_actions[0]['pip'] = act[1].amount
            my_actions[0]['pip'] = 2 * act[1].amount
        act = hand.pop()
        my_actions['won'] = act[0] == self.name
        opp_actions['won'] = not my_actions['won']
        won_amount = act[1].amount/2.0
        this_hand = {self.name:my_actions, self.opponent['name']:opp_actions, 'steal':False, 'limp':False}
        hand.popleft() # second action is always bb posting, and is useless
        street = 0 #0 is preflop, 1 is flop, 2 is turn and 3 is river 
        first = True
        pot = 0
        pip = {self.name:0, self.opponent['name']:0}
        while len(hand) > 0 :
            act = hand.popleft()
            #print "parsing action: ",act
            if act[0] == 'Dealer': #then this action corresponds to changing street
                street += 1
                if street == 1:
                    if opp_actions['position']:
                        self.opp_stats['^HPFSB'] += 1
                    else:
                        self.opp_stats['^HPFBB'] += 1
                elif street == 2:
                    self.opp_stats['^HPT'] += 1
                elif street == 3:
                    self.opp_stats['^HPR'] += 1
                continue
            #print "on street: ", street
            action = self.classify(act[1])
            if first:   
                first = False
                if action == RAISE:
                    this_hand['steal'] = True
                elif action == CALL:
                    this_hand['limp'] = True

            if act[0] in [self.name, self.opponent['name']]:
                if action == RAISE:
                    this_hand[act[0]][street]['raises'] += 1
                    this_hand[act[0]][street]['pip'] = act[1].amount
                elif action == CHECK:
                    this_hand[act[0]][street]['checks'] += 1
                elif action == CALL:
                    this_hand[act[0]][street]['calls'] += 1
                    this_hand[act[0]][street]['pip'] = this_hand[self.name if act[0] == self.opponent['name'] else self.opponent['name']][street]['pip']
                elif action == FOLD:
                    this_hand[act[0]][street]['folds'] += 1
                    if street == 0 and act[0] == self.name:
                        if opp_actions['position']:
                            self.opp_stats['^HPFSB'] += 1
                        else:
                            self.opp_stats['^HPFBB'] += 1
                elif action == BET:
                    this_hand[act[0]][street]['bets'] += 1
                    if street == FLOP and act[0] == self.opponent['name']:
                        pot = sum([my_actions[x]['pip'] for x in range(4)])+sum([opp_actions[x]['pip'] for x in range(4)])
                        if act[1].amount < .5*pot:
                            self.cory_stats['^W'] += 5
                        elif act[1].amount > pot:
                            self.cory_stats['^A'] += 10
                        if my_actions['position']: #he's BB
                            self.cory_stats['^A'] += 5
                    this_hand[act[0]][street]['pip'] = act[1].amount
            elif DEBUG:
                print "unknown player: ",act[0]

        #update relevant statistics
        #print "tallied up my actions",my_actions
        #print "tallied up opp actions",opp_actions
        self.my_stats['hands'] += 1
        self.opp_stats['hands'] += 1

        if opp_actions['won']:
            hand = last[:]
            hand.pop()
            act = hand.pop()
            while act[0] != self.opponent['name'] or isinstance(act[1],Show) or isinstance(act[1],Won):
                act= hand.pop()
            action = self.classify(act[1])
            if action == RAISE:
                self.cory_stats['^A'] += 20
            if action in [BET, RAISE, CALL]:
                if act[1].amount >= min(self.opp_stack,self.my_stack):
                    self.cory_stats['^A'] += 10
                    self.opp_stats['^HAI'] +=1
                else:   
                    self.cory_stats['^C'] += 20
        if my_actions['won']:
            self.my_stack += won_amount
            self.opp_stack -= won_amount
        else:
            self.my_stack -= won_amount
            self.opp_stack += won_amount
            
        self.update_stats(self.opp_stats, my_actions, opp_actions, this_hand['steal'], this_hand['limp'])
        self.update_stats(self.my_stats, opp_actions, my_actions, this_hand['steal'], this_hand['limp'])
        
        self.calc_cory(self.cory_stats, my_actions, opp_actions, this_hand['steal'], this_hand['limp'])
        
    def calc_cory(self, stats, me, opp, steal, limp):
        stats['^A'] += 5*sum([opp[x][y] for x in range(4) for y in ['bets', 'raises']])
        stats['^A'] += 10*sum([max(opp[x]['raises']-1,0) for x in range(4)])
        stats['^C'] += 5*sum([opp[x][y] for x in range(4) for y in ['bets', 'raises', 'calls']])
        stats['^C'] += 10*sum([opp[x]['calls']>0 for x in range(4) if opp[x]['raises']>0])
        stats['^W'] += 5*(limp and opp['position'])
        stats['^W'] += 3*(opp[PREFLOP]['folds']>0)
        stats['^W'] += 5*(sum([opp[x]['folds'] for x in [FLOP,TURN,RIVER]])>0)
        stats['^A'] += 20*sum([1 for x in [FLOP,TURN,RIVER] if opp[x]['checks']>0 and me[x]['bets'] >0 and opp[x]['raises']>0])
        stats['A'] = stats['^A']/float(self.opp_stats['hands'])
        stats['C'] = stats['^C']/float(self.opp_stats['hands'])
        stats['W'] = stats['^W']/float(self.opp_stats['hands'])

    def new_hand(self):
        return

    def update_stats(self,stats,me,opp,steal,limp):
        this_hand = {}
        vpip_den = [stats['hands'], stats['^HPFBB']+stats['^HPFSB'], stats['^HPT'], stats['^HPR']]
        for street in range(4):
            if opp[street]['raises'] or opp[street]['bets'] or opp[street]['calls']:
                stats['^VPIP'][street] += 1
            if opp[street]['raises']:
                stats['^INCR'][street] += 1
            stats['VPIP'][street] = stats['^VPIP'][street]/float(vpip_den[street]) if (vpip_den[street] and vpip_den[street] >0) else None
            stats['INCR'][street] = stats['^INCR'][street]/float(vpip_den[street]) if (vpip_den[street] and vpip_den[street] >0) else None
        this_hand['^AF'] = sum([opp[x]['raises'] + opp[x]['bets'] for x in [FLOP, TURN, RIVER]])
        this_hand['_AF'] = sum([opp[x]['calls'] for x in [FLOP, TURN, RIVER]])
        
        #PREFLOP
        this_hand['^ST'] = steal and opp['position']
        this_hand['^LMP']= limp and opp['position']
        this_hand['_3B'] = steal and not opp['position']
        this_hand['^FBB']= this_hand['_3B'] and opp[0]['folds'] and opp[0]['raises'] == 0
        this_hand['^3B'] = this_hand['_3B'] and opp[0]['raises'] > 0
        this_hand['_4B'] = this_hand['^ST'] and me[0]['raises'] > 0
        this_hand['^F3B']= this_hand['_4B'] and opp[0]['folds'] and opp[0]['raises'] == 1
        this_hand['^4B'] = this_hand['_4B'] and opp[0]['raises'] >= 2
        this_hand['_F4B']= this_hand['^3B'] and me[0]['raises'] >= 2
        this_hand['^F4B']= this_hand['_F4B']and opp[0]['folds'] and opp[0]['raises'] == 1
        
        #FLOP
        this_hand['_COB'] = opp['position'] and opp[0]['raises'] > 0 and me[0]['calls']>0 and me[1]['checks']>0
        this_hand['^COB'] = this_hand['_COB'] and opp[1]['bets'] > 0
        this_hand['_FCOB']= not opp['position'] and me[0]['raises']>0 and opp[0]['calls']>0 and opp[1]['checks']>0 and me[1]['bets']>0
        this_hand['^FCOB']= this_hand['_FCOB'] and opp[1]['folds']>0

        #TURN
        this_hand['_2COB'] = this_hand['^COB'] and me[2]['checks']>0
        this_hand['^2COB'] = this_hand['_2COB'] and opp[2]['bets']>0
        this_hand['_F2COB']= this_hand['_FCOB'] and me[2]['bets']>0
        this_hand['^F2COB']= this_hand['_F2COB'] and opp[2]['folds']>0
        
        this_hand['_CHBR'] = [0,0,0,0]
        this_hand['^CHBR'] = [0,0,0,0]
        
        #POSTFLOP
        for street in [FLOP, TURN, RIVER]:
            this_hand['_CHBR'][street] = opp[street]['checks']>0 and me[street]['bets'] >0
            this_hand['^CHBR'][street] = this_hand['_CHBR'][street] and opp[street]['raises']>0
        
        #print "and for this hand, here are our stats:"
        #print this_hand
        
        for stat in stats.keys():
            if this_hand.has_key(stat) and isinstance(this_hand[stat],int):
                stats[stat] += this_hand[stat]
        stats['AF'] = stats['^AF']/float(stats['_AF']) if stats['_AF'] else None
        stats['ST'] = stats['^ST']/float(stats['hands']) * 2.0
        stats['LMP'] = stats['^LMP']/float(stats['hands']) * 2.0
        stats['FBB'] = stats['^FBB']/float(stats['_3B']) if stats['_3B'] else None
        stats['3B'] = stats['^3B']/float(stats['_3B']) if stats['_3B'] else None
        stats['F3B'] = stats['^F3B']/float(stats['_4B']) if stats['_4B'] else None
        stats['4B'] = stats['^4B']/float(stats['_4B']) if stats['_4B'] else None
        stats['F4B'] = stats['^F4B']/float(stats['_F4B']) if stats['_F4B'] else None
        stats['COB'] = stats['^COB']/float(stats['_COB']) if stats['_COB'] else None
        stats['FCOB'] = stats['^FCOB']/float(stats['_FCOB']) if stats['_FCOB'] else None
        stats['2COB'] = stats['^2COB']/float(stats['_2COB']) if stats['_2COB'] else None
        stats['F2COB'] = stats['^F2COB']/float(stats['_F2COB']) if stats['_F2COB'] else None
        stats['HAI'] = stats['^HAI']/float(stats['hands'])
        stats['HPFBB'] = stats['^HPFBB']/float(stats['hands']) * 2.0
        stats['HPFSB'] = stats['^HPFSB']/float(stats['hands']) * 2.0
        stats['HPT'] = stats['^HPT']/float(stats['^HPFBB']+stats['^HPFSB']) if (stats['^HPFBB'] > 0 or stats['^HPFSB'] > 0) else None
        stats['HPR'] = stats['^HPR']/float(stats['^HPT']) if stats['^HPT'] else None
        for street in [FLOP, TURN, RIVER]:
            stats['_CHBR'][street] += this_hand['_CHBR'][street]
            stats['^CHBR'][street] += this_hand['^CHBR'][street]
            stats['CHBR'][street] = stats['^CHBR'][street]/float(stats['_CHBR'][street]) if stats['_CHBR'][street] else None

    def respond(self):
        #print self.opp_stats
        if self.hands_played == 0:
            self.bot_to_use = self.bot
            if self.last_name != self.opponent['name']:
                self.last_name = self.opponent['name']
                self.restart()
                if self.bots:
                    for b in self.bots:
                        b.losses = 0
                    self.bot = self.bots[0]
                    self.index = 0
            
        if DEBUG: print self.name
        if DEBUG: print self.hands_played, self.last_hand, self.hands_played_against, self.hand, self.board
        if DEBUG: print self.actions, self.opponent
        if DEBUG: print self.legal
        self.calculate_ev()
        if DEBUG: print "ev=%d, pot=%d" % (self.ev*100, self.pot)
        if self.hands_played != self.last_hand and self.hands_played:
            if self.hands_played > self.last_hand:
                self.hands_played_against += self.hands_played - self.last_hand
            else:
                self.hands_played_against += 1
            if self.hands_played >= self.last_hand + 2: #if we missed one
                self.calculate_stats(self.last[0])
            self.calculate_stats(self.last[1])
            self.last_hand = self.hands_played
            self.opp_hand = 100.0
            self.opp_last_stack = self.opponent['stack'] + self.opponent['pip']
            #self.bot.new_hand() #notify our bot of new hand
            if self.low_chip_bot or self.high_chip_bot:
                if self.low_chip_bot and self.stack + self.pip < 75:
                    if self.low_chip_bot != self.bot_to_use:
                        if DEBUG: print "using low stack bot"
                        self.bot_to_use = self.low_chip_bot
                elif self.high_chip_bot and self.stack + self.pip > 600:
                    if self.high_chip_bot != self.bot_to_use:
                        if DEBUG: print "using high stack bot"
                        self.bot_to_use = self.high_chip_bot
                else:
                    if self.bot != self.bot_to_use:
                        if DEBUG: print "using normal bot"
                        self.bot_to_use = self.bot
            if not self.bot_to_use:
                self.bot_to_use = self.bot
            if DEBUG: print self.opp_stats
            if DEBUG: print self.opp_stack, self.my_stack
            if DEBUG: raw_input()
        action = self.bot_to_use.respond(self)
        if DEBUG: print "and ourbot sees action of", action
        return action
Пример #21
0
class PokerHandEval:
    def __init__(self):
        self.hand_groups = {
            "A":["AA", "AKs", "KK"],
            "B":["AK", "QQ"],
            "C":["JJ", "TT"],
            "D":["AQs", "AQ", "AJs", "99", "88"],
            "E":["AJ","ATs","KQs", "77","66","55"],
            "F":["AT","KQ","KJs","QJs","44","33","22"],
            "G":["A9s","A8s","A7s","A6s","A5s","A4s","A3s","A2s","KTs","QTs","JTs","J9s","T9s","98s"],
            "H":["KJ","KT","QJ","J8s","T8s","87s","76s"]
        }
        self.hand_values = {"A":13,"K":12,"Q":11,"J":10, "T":9,"9":8,"8":7,"7":6,"6":5,"5":4,"4":3,"3":2,"2":1}
        self.odds_map = {
            "flop":{1:0.045,2:0.088,3:0.13,4:0.172,5:0.212,6:0.252,7:0.29,8:0.327,9:0.364,10:0.399,11:0.433,12:0.467,13:0.499,14:0.53,15:0.561,16:0.59,17:0.618},
            "turn":{1:0.023,2:0.045,3:0.68,4:0.091,5:0.114,6:0.136,7:0.159,8:0.182,9:0.205,10:0.227,11:0.25,12:0.273,13:0.295,14:0.318,15:0.341,16:0.364,17:0.386}
        }
        self.eval = PokerEval()
    def prepareHand(self, hand):
        h = hand.split(" ")
        if self.hand_values[h[1][0]] > self.hand_values[h[0][0]]:
            self.hand = "%s%s" % (h[1][0],h[0][0])
        else:
            self.hand = "%s%s" % (h[0][0],h[1][0])
        if h[0][1] == h[1][1]:
            self.hand += "s"
    def getHandGroup(self):
        for group in self.hand_groups:
            if self.hand in self.hand_groups[group]:
                return group
        return False
    def getHandValue(self, game, serial):
        hand = game.getHandAsString(serial)
        board = game.getBoardAsString()
        board_list = board.split(" ")
        if len(board_list) < 5:
            for i in range(len(board_list), 5):
                board_list.append("__")
        hand_list = hand.split(" ")
        cards = hand_list + board_list
        return self.eval.best_hand("hi", self.eval.string2card(cards), [] )
    def parseHistory(self, hist):
        self.round_action = {}
        self.action2serials = {
            "call":[],
            "raise":[],
            "fold":[]
        }
        self.serial2action = {}
        ret = ""
        for event in hist:
            type = event[0]
            if type in ["fold","check","call","raise"]:
                if len(event) == 3:
                    (action, serial, amount) = event
                else:
                    (action,serial) = event
                    amount = False
                ret = "action: %s, serial:%d" % (action, serial)
                if amount:
                    ret += ", amount = %d" % amount
                    self.round_action[serial] = [action, amount]
                else:
                    self.round_action[serial] = [action]
                self.serial2action[serial] = action
                if action in self.action2serials.keys():
                    if not serial in self.action2serials[action]:
                        self.action2serials[action].append(serial)
    def getPosition(self, game, serial):
        me = game.serial2player[serial]
        players = game.serialsAllSorted()
        for player in players:
            user = game.serial2player[player]
        user_positions = {}
        player_seats = {}
        i=1
        for p in game.serialsAllSorted():
            user = game.serial2player[p]
            player_seats[user.seat] = p
        max_seat = len(player_seats)
        early = max_seat / 3
        middle = early * 2
        self.my_seat = me.seat
        self.serial2position = {}
        self.position2serials = {
            "early":[],
            "middle":[],
            "late":[]
        }
        for p in player_seats.keys():
            player_serial = player_seats[p]
            if i <= early:
                position = "early"
            elif i >= (early + 1) and i <= middle:
                position = "middle"
            else:
                position = "late"
            if not player_serial in self.serial2position.keys():
                self.serial2position[player_serial] = position
            if not player_serial in self.position2serials[position]:
                self.position2serials[position].append(player_serial)
            if p == self.my_seat:
                self.position = position
            i += 1
Пример #22
0
import sys
sys.path.insert(0, ".")
sys.path.insert(0, ".libs")

from pokereval import PokerEval
from random import shuffle

card1 = sys.argv[1]
card2 = sys.argv[2]
players = int(sys.argv[3])
iterations = int(sys.argv[4])


wins = 0

pe = PokerEval()

for iter in range(0,iterations):
  #generate a deck
  deck = ['Ac', '2c', '3c', '4c', '5c', '6c', '7c', '8c', '9c', 'Tc', 'Jc', 'Qc', 'Kc',
	  'Ad', '2d', '3d', '4d', '5d', '6d', '7d', '8d', '9d', 'Td', 'Jd', 'Qd', 'Kd',
	  'Ah', '2h', '3h', '4h', '5h', '6h', '7h', '8h', '9h', 'Th', 'Jh', 'Qh', 'Kh', 
	  'As', '2s', '3s', '4s', '5s', '6s', '7s', '8s', '9s', 'Ts', 'Js', 'Qs', 'Ks']
  shuffle(deck)
  
  #add all players to 'pockets'
  pockets = []
  for i in range(0,players):
    pockets.append([])
    
  # Your cards
Пример #23
0
# c = copas
# s = espadas
# h = paus
# d = ouros

# Values:
# 2 .. 9
# T = 10
# J, Q, K, A
# Unknown = __
import timeit
from pokereval import PokerEval

__author__ = 'gogo40'

pe = PokerEval()

ranks_ = ["h", "c", "d", "s"]

game_ = "holdem"
iterations_ = 5000000
dead_ = []


#######################################
# h_power calculator
def h_power_calc(result_):
    total_ = 0.0
    ev_ = []
    for r in result_['eval']:
        v = float(r['ev'])
Пример #24
0
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301, USA.
#
# http://gna.org/support/?1823
#
import sys

sys.path.insert(0, ".")
sys.path.insert(0, ".libs")

from pokereval import PokerEval

pokereval = PokerEval()

result = pokereval.poker_eval(
    game="holdem", fill_pockets=1, pockets=[["As", "3s"], ["__", "__"]], dead=[], board=["Ad", "Qs", "2c", "Ac", "Kc"]
)
assert result == {
    "info": (990, 0, 1),
    "eval": [
        {"winlo": 0, "tielo": 0, "winhi": 877, "scoop": 877, "loselo": 0, "ev": 903, "losehi": 78, "tiehi": 35},
        {"winlo": 0, "tielo": 0, "winhi": 78, "scoop": 78, "loselo": 0, "ev": 96, "losehi": 877, "tiehi": 35},
    ],
}

result = pokereval.poker_eval(
    game="omaha8",
    fill_pockets=1,
Пример #25
0
#!/usr/bin/python

from pokereval import PokerEval

p = PokerEval()

contador = 0
with open('./p054_poker.txt') as archivo:
    for juego in archivo:
        cartas = juego.rstrip().lower().split(' ')

        mano_a, mano_b = cartas[:5], cartas[5:]

        if p.evaln(mano_a) > p.evaln(mano_b):
            contador += 1

print contador
Пример #26
0
class Table(object):
    def __init__(self, protocol, avatar, table_info):
        self.protocol = protocol
        self.id = table_info.get('id', 0)
        self.seat = table_info.get('player_seated', -1)
        self.seats = [0] * table_info.get('seats', 10)
        if self.seat != -1:
            self.seats[self.seat] = avatar.serial
            assert avatar.seat == self.seat, "as %s, ss %s" % (avatar.seat,
                                                               self.seat)
        self.name = table_info.get('name', 'unnamed')
        self.betting_structure = table_info['betting_structure']
        blinds, buy_ins, limit = table_info['betting_structure'].split('_')
        min_buy_in, max_buy_in = buy_ins.split('-')
        small, big = blinds.split('-')

        self.max_buy_in = int(max_buy_in) * 100
        self.min_buy_in = int(min_buy_in) * 100
        self.big_blind = int(big) * 100
        self.small_blind = int(small) * 100

        self.players = {avatar.serial: avatar}
        self.avatar = avatar
        self._serial_and_game_id = dict(serial=avatar.serial, game_id=self.id)
        self._eval = PokerEval()
        self.reset()
        self._game_state = GAME_STATE_NULL

    def reset(self):
        """reseting game states for a new hand"""
        self.board_cards = []
        self.position = -1
        self._reset_players()

    def getBoardCards(self):
        """return a list of board games"""
        return list(map(lambda x: x & 63, self.board_cards))

    def getAvatarInfo(self):
        """return a string of usefull information about the avatar"""
        return ", ".join(self._get_avatar_info())

    def isInPosition(self, serial):
        """returs true if player with serial is in position"""
        return serial in self.in_game and self.position == self.in_game.index(
            serial)

    def logIt(self, astr, prefix=" [D] "):
        """a little helper function to log output"""
        self.protocol.logIt(astr, prefix=prefix)

    def updateSeats(self, seats):
        """update seat information"""
        for index, (old, new) in enumerate(zip(self.seats, seats)):
            if old == 0 and new != 0:
                self.addPlayer(index, new)
            elif old != 0 and new == 0:
                self.removePlayer(index)
            elif old != new:
                self.removePlayer(index)
                self.addPlayer(index, new)
                self.logIt("warning idx %s, old %s, new %s" %
                           (index, old, new))

    def addPlayer(self, index, serial):
        """Add player to this table"""
        self.seats[index] = serial
        # Request more information about this player
        if serial == self.avatar.serial:
            self.players[index] = self.avatar
        else:
            self.protocol.sendPacket(
                networkpackets.PacketPokerGetUserInfo(serial=serial))

    def removePlayer(self, index):
        """remove player from this table"""
        serial = self.seats[index]
        self.seats[index] = 0
        if serial in self.players:
            del self.players[serial]

    def updatePlayer(self, player_info):
        """update general palyer information (we requested them in addPlayer)"""
        player = self._get_or_create_player(**player_info)
        player.update(player_info)

    def updatePlayerChips(self, serial, chips, bet):
        """update players chips"""
        player = self._get_or_create_player(serial=serial)
        return player.updateChips(chips, bet)

    def updatePlayerCards(self, serial, cards):
        """update players cards"""
        player = self._get_player(serial)
        player.updateCards(cards)

    def rebuy(self, serial, amount):
        """update money state of player because a rebuy happend"""
        player = self._get_player(serial)
        player.rebuy(amount)

    def _reset_players(self):
        """reset player states"""
        for player in self.players.values():
            player.reset()

    def highestBetNotFold(self):
        """returns the highest bet of all players that are not fold"""
        return max([0] + [
            p._bet for p in self.players.values()
            if p.serial in self.in_game and p.notFold()
        ])

    def inSmallBlindPosition(self):
        """returns True if the player in position is in small_blind position"""
        return len(self.in_game) > 0 and ((self.dealer + 1) %
                                          len(self.in_game)) == self.position

    def bigBlind(self):
        """returns the big_blind of the current table"""
        return self.big_blind or 0

    def doBuyIn(self):
        """actually request a buy_in"""
        self.protocol.sendPacket(
            networkpackets.PacketPokerBuyIn(amount=self.max_buy_in,
                                            **self._serial_and_game_id))
        self.protocol.sendPacket(
            networkpackets.PacketPokerAutoBlindAnte(
                **self._serial_and_game_id))

    def doRebuy(self, amount):
        """actually request a rebuy"""
        self.protocol.sendPacket(
            networkpackets.PacketPokerRebuy(amount=amount,
                                            **self._serial_and_game_id))

    def doSit(self):
        """actually request a sit"""
        self.protocol.sendPacket(
            networkpackets.PacketPokerSit(**self._serial_and_game_id))

    def doSitOut(self):
        """actually request a sitout"""
        self.protocol.sendPacket(
            networkpackets.PacketPokerSitOut(**self._serial_and_game_id))

    def doQuit(self):
        """actually request a table quit"""
        self.protocol.sendPacket(
            networkpackets.PacketPokerTableQuit(**self._serial_and_game_id))

    def doFold(self):
        """actually request a fold"""
        self.protocol.sendPacket(
            networkpackets.PacketPokerFold(**self._serial_and_game_id))

    def doCheck(self):
        """actually request a check"""
        self.protocol.sendPacket(
            networkpackets.PacketPokerCheck(**self._serial_and_game_id))

    def doCall(self):
        """actually request a call"""
        self.protocol.sendPacket(
            networkpackets.PacketPokerCall(**self._serial_and_game_id))

    def doAllIn(self):
        """actually raise all chips"""
        self.doRaise(self.avatar.getChips())

    def doRaise(self, amount):
        """
            actually request a raise by a given amount.
            WARNING: If the amount you requested is too low, the raise will be accepted but the 
            minimum amount to raise will be used instead. You will be informend about the amount 
            that is used to raise.
        """
        self.protocol.sendPacket(
            networkpackets.PacketPokerRaise(amount=amount,
                                            **self._serial_and_game_id))

    def explain(self, packet, state):
        """packets that might be interesting for the game will be handled here"""
        def handlePacketPokerBuyInLimits(packet):
            self.max_buy_in = packet.max
            self.min_buy_in = packet.min

        def handlePacketPokerSeats(packet):
            return self.updateSeats(packet.seats)

        def handlePacketPokerPlayerInfo(packet):
            self.updatePlayer(packet.__dict__)

        def handlePacketPokerPlayerChips(packet):
            return self.updatePlayerChips(packet.serial,
                                          chips=packet.money,
                                          bet=packet.bet)

        def handlePacketPokerPlayerArrive(packet):
            self.updatePlayer(packet.__dict__)

        def handlePacketPokerPlayerLeave(packet):
            self.removePlayer(packet.seat)

        def handlePacketPokerSit(packet):
            self._get_player(packet.serial).sit()

        def handlePacketPokerSitOut(packet):
            self._get_player(packet.serial).sitOut()

        def handlePacketPokerRebuy(packet):
            assert self.id == packet.game_id
            self.rebuy(packet.serial, packet.amount)

        def handlePacketPokerInGame(packet):
            assert self.id == packet.game_id
            self.in_game = packet.players

        def handlePacketPokerPosition(packet):
            assert self.id == packet.game_id
            self.position = packet.position

        def handlePacketPokerStart(packet):
            assert self.id == packet.game_id
            self.reset()
            self.hand_serial = packet.hand_serial

        def handlePacketPokerDealer(packet):
            assert self.id == packet.game_id
            # assert self.dealer == packet.previous_dealer
            self.dealer = packet.dealer

        def handlePacketPokerPlayerCards(packet):
            self.updatePlayerCards(packet.serial, packet.cards)
            if packet.serial == self.avatar.serial:
                self.logIt("You got %r" % self._cards_to_string(packet.cards))

        def handlePacketPokerBoardCards(packet):
            self.board_cards = packet.cards

        def handlePacketPokerRaise(packet):
            self._get_player(packet.serial).bet(packet.amount)

        def handlePacketPokerCall(packet):
            player = self._get_player(packet.serial)
            highestbet = self.highestBetNotFold()
            bigb = self.bigBlind(
            ) if self._game_state == GAME_STATE_PRE_FLOP and not self.inSmallBlindPosition(
            ) else 0
            # import rpdb2; rpdb2.start_embedded_debugger("haha")
            self.logIt("%r, %r" % (highestbet, bigb))
            amount = min(max(highestbet, bigb) - player._bet, player.money)
            player.bet(amount)

        def handlePacketPokerState(packet):
            self._game_state = packet.string

        def handlePacketPokerBlind(packet):
            self._get_player(packet.serial).bet(packet.amount)

        try:
            handle = locals()["handle" + packet.__class__.__name__]
            return handle(packet)
        except KeyError:
            # self.logIt(" explain cant handle : %r" % packet.__class__.__name__)
            return True
        except Exception:
            exc_type, exc_value, exc_traceback = sys.exc_info()
            self.logIt(packet.__class__.__name__,
                       prefix=" EEE  handle failed: ")

            for exline in traceback.format_exception(exc_type, exc_value,
                                                     exc_traceback):
                for line in exline.split('\n'):
                    self.logIt(str(line), prefix=" EEE ")

    def _cards_to_string(self, cards):
        """return a string for cards in a human readable way"""
        return repr(self._eval.card2string(map(lambda x: x & 63, cards)))\
            #.lower().replace("h", u"\u2761").replace("s", u"\u2660").replace("c", u"\u2663").replace("d", u"\u2662")

    def _get_or_create_player(self, serial, seat=None, **player_info):
        """returns the player with the serial, the player will be created if it does not exist yet"""
        # serial = player_info['serial']
        # seat = player_info['seat']
        if seat and self.seats[seat] != 0 and serial != self.seats[seat]:
            self.logIt("%s is allready on seat %s, cleared" %
                       (self.seats[seat], seat))
            del self.players[self.seats[seat]]
            self.seats[seat] = serial

        if serial not in self.players:
            self.players[serial] = Player(serial=serial,
                                          seat=seat,
                                          **player_info)

        return self.players[serial]

    def _get_player(self, serial):
        """returns the player, raises an IndexError if it does not exist"""
        return self.players[serial]

    def _log_players(self):
        """ log player informations """
        self.logIt("Players:")
        for player in self.players.itervalues():
            self.logIt(player._player_info())
        self.logIt("")

    def getDebugLines(self):
        """returns a list of debug lines (yellow box)"""
        return self._get_table_info() + self._get_avatar_info(
        ) + self._get_player_info()

    @catcher
    def _get_table_info(self):
        """returns a list of table informations"""
        highestbet = self.highestBetNotFold(),
        bigb = self.bigBlind(
        ) if self._game_state == GAME_STATE_PRE_FLOP and not self.inSmallBlindPosition(
        ) else 0
        return [
            "blinds: small:%r big:%r" % (self.small_blind, self.big_blind),
            "buy_ins: min:%r max:%r" % (self.min_buy_in, self.max_buy_in),
            "bs: %r" % self.betting_structure,
            "highestbet = %r" % highestbet,
            "bigb = %r" % bigb,
        ]

    @catcher
    def _get_player_info(self):
        """returns a list with player informations for all players"""
        return [player._player_info() for player in self.players.values()]

    @catcher
    def _get_avatar_info(self):
        """returns informations of the avatar that is currently logged in"""
        retvals = []
        if self.avatar.cards:
            retvals.append("hand: " + self._cards_to_string(self.avatar.cards))
        if self.board_cards:
            retvals.append("board: " + self._cards_to_string(self.board_cards))
            if self.avatar.cards:
                best_hand = self._eval.best_hand(
                    "hi",
                    self.avatar.getCards() + self.getBoardCards())
                desc = best_hand.pop(0)
                retvals.append("%s: %s" %
                               (desc, self._cards_to_string(best_hand)))
        return retvals
Пример #27
0
from flask import Flask, request, jsonify
from pokereval import PokerEval

GAME = 'holdem'
ITERATIONS = 20000

app = Flask(__name__)
pe = PokerEval()


@app.route('/', methods=['POST', 'GET'])
def index():
    app.logger.info('index route')
    if request.method == 'POST':
        data = request.get_json()
        app.logger.info('request {}'.format(data))
        equities = pe.poker_eval(iterations=ITERATIONS, game=GAME, **data)
        app.logger.info('equities {}'.format(equities))
        return jsonify(equities)
    return 'https://github.com/minmax/pypoker-eval'


app.run(host='0.0.0.0', port=5000, debug=True)
Пример #28
0
class HandEvaluator:
    evaluator = PokerEval()

    preflop_win_percentages_suited = [
        [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
        [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
        [
            0, 0, 0, 0.3598, 0.3682, 0.3784, 0.3766, 0.3814, 0.4026, 0.4241,
            0.4484, 0.4738, 0.5017, 0.532, 0.5737
        ],
        [
            0, 0, 0.3598, 0, 0.3863, 0.3968, 0.3953, 0.4003, 0.4087, 0.4325,
            0.4568, 0.4823, 0.5101, 0.5405, 0.5821
        ],
        [
            0, 0, 0.3682, 0.3863, 0, 0.4145, 0.4133, 0.4184, 0.427, 0.4385,
            0.4653, 0.4906, 0.5185, 0.5488, 0.5903
        ],
        [
            0, 0, 0.3784, 0.3968, 0.4145, 0, 0.4313, 0.4367, 0.4454, 0.4572,
            0.4721, 0.4999, 0.5276, 0.5579, 0.5992
        ],
        [
            0, 0, 0.3766, 0.3953, 0.4133, 0.4313, 0, 0.4536, 0.4623, 0.4742,
            0.4894, 0.506, 0.536, 0.5664, 0.599
        ],
        [
            0, 0, 0.3814, 0.4003, 0.4184, 0.4367, 0.4536, 0, 0.4793, 0.4912,
            0.5064, 0.5232, 0.543, 0.5753, 0.6098
        ],
        [
            0, 0, 0.4026, 0.4087, 0.427, 0.4454, 0.4623, 0.4793, 0, 0.5079,
            0.5233, 0.5401, 0.5601, 0.5831, 0.6194
        ],
        [
            0, 0, 0.4241, 0.4325, 0.4385, 0.4572, 0.4742, 0.4912, 0.5079, 0,
            0.5402, 0.5566, 0.5766, 0.5998, 0.6277
        ],
        [
            0, 0, 0.4484, 0.4568, 0.4653, 0.4721, 0.4894, 0.5064, 0.5233,
            0.5402, 0, 0.5752, 0.5947, 0.6178, 0.6459
        ],
        [
            0, 0, 0.4738, 0.4823, 0.4906, 0.4999, 0.506, 0.5232, 0.5401,
            0.5566, 0.5752, 0, 0.6026, 0.6256, 0.6539
        ],
        [
            0, 0, 0.5017, 0.5101, 0.5185, 0.5276, 0.536, 0.543, 0.5601, 0.5766,
            0.5947, 0.6026, 0, 0.6339, 0.6621
        ],
        [
            0, 0, 0.532, 0.5405, 0.5488, 0.5579, 0.5664, 0.5753, 0.5831,
            0.5998, 0.6178, 0.6256, 0.6339, 0, 0.6704
        ],
        [
            0, 0, 0.5737, 0.5821, 0.5903, 0.5992, 0.599, 0.6098, 0.6194,
            0.6277, 0.6459, 0.6539, 0.6621, 0.6704, 0
        ]
    ]

    preflop_win_percentages_unsuited = [
        [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
        [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
        [
            0, 0, 0.5033, 0.3229, 0.3319, 0.3428, 0.3406, 0.3458, 0.3682,
            0.3909, 0.4165, 0.4434, 0.4729, 0.5051, 0.5492
        ],
        [
            0, 0, 0.3229, 0.5368, 0.3514, 0.3625, 0.3607, 0.3659, 0.3747,
            0.4001, 0.4259, 0.4527, 0.4821, 0.5142, 0.5584
        ],
        [
            0, 0, 0.3319, 0.3514, 0.5702, 0.3815, 0.3801, 0.3854, 0.3944,
            0.4067, 0.4349, 0.4618, 0.4912, 0.5232, 0.5672
        ],
        [
            0, 0, 0.3428, 0.3625, 0.3815, 0.6032, 0.3994, 0.4051, 0.4143,
            0.4266, 0.4424, 0.4717, 0.5011, 0.5331, 0.5769
        ],
        [
            0, 0, 0.3406, 0.3607, 0.3801, 0.3994, 0.6328, 0.4232, 0.4323,
            0.4449, 0.4608, 0.4784, 0.5102, 0.5421, 0.5768
        ],
        [
            0, 0, 0.3458, 0.3659, 0.3854, 0.4051, 0.4232, 0.6623, 0.4505,
            0.463, 0.479, 0.4968, 0.5176, 0.5518, 0.5883
        ],
        [
            0, 0, 0.3682, 0.3747, 0.3944, 0.4143, 0.4323, 0.4505, 0.6915,
            0.4809, 0.4971, 0.5149, 0.536, 0.5602, 0.5986
        ],
        [
            0, 0, 0.3909, 0.4001, 0.4067, 0.4266, 0.4449, 0.463, 0.4809,
            0.7205, 0.5153, 0.5324, 0.5536, 0.578, 0.6076
        ],
        [
            0, 0, 0.4165, 0.4259, 0.4349, 0.4424, 0.4608, 0.479, 0.4971,
            0.5153, 0.7501, 0.5524, 0.5728, 0.5973, 0.6271
        ],
        [
            0, 0, 0.4434, 0.4527, 0.4618, 0.4717, 0.4784, 0.4968, 0.5149,
            0.5324, 0.5524, 0.7747, 0.5813, 0.6057, 0.6355
        ],
        [
            0, 0, 0.4729, 0.4821, 0.4912, 0.5011, 0.5102, 0.5176, 0.536,
            0.5536, 0.5728, 0.5813, 0.7992, 0.6145, 0.6442
        ],
        [
            0, 0, 0.5051, 0.5142, 0.5232, 0.5331, 0.5421, 0.5518, 0.5602,
            0.578, 0.5973, 0.6057, 0.6145, 0.8239, 0.6531
        ],
        [
            0, 0, 0.5492, 0.5584, 0.5672, 0.5769, 0.5768, 0.5883, 0.5986,
            0.6076, 0.6271, 0.6355, 0.6442, 0.6531, 0.852
        ]
    ]

    def card_to_str(card):
        """
        Convert this card to a string or number for pypoker-eval.
        Note that I don't check whether you passed a Card or the right string
        format!
        """
        # NOT str! Could be unicode
        if isinstance(card, basestring):
            return card
        return card.__str__()

    def str_to_card(card_string):
        """
        Convert this string to a pokerbots.engine.game.Card instance.
        Note that I don't check whether or not you passed the right format!
        """
        if isinstance(card_string, Card):
            return card
        rank_str = card_string[0].lower()
        suit_str = card_string[1].lower()
        rank = 2
        suit = 1
        if rank_str == "t":
            rank = 10
        elif rank_str == "j":
            rank = 11
        elif rank_str == "q":
            rank = 12
        elif rank_str == "k":
            rank = 13
        elif rank_str == "a":
            rank = 14
        if suit_str == "s":
            suit = 1
        elif suit_str == "h":
            suit = 2
        elif suit_str == "d":
            suit = 3
        elif suit_str == "c":
            suit = 4
        return Card(rank, suit)

    def evaluate_hand(hand, board=[], iterations=1000):
        """
        Return winning percentage of your hand, with ties counted as 0.5
        Includes Monte-Carlo simulation of running the board.
        Includes trying all possible opponent hands.
        Arguments:
        hand: your hand
        board: the board if any
        iterations: number of times to simulate
        """
        # If the board is determined, there's only 990 hands to run,
        # so run them all
        if len(board) == 5:
            # convert to pypoker-eval format
            hand = map(HandEvaluator.card_to_str, hand)
            board = map(HandEvaluator.card_to_str, board)
            poker_eval_result = HandEvaluator.evaluator.poker_eval(
                game="holdem",
                pockets=[hand, [255, 255]],
                dead=[],
                board=board)
        elif len(board) == 0:
            # Use a lookup table, because this has been done before
            if hand[0].suit == hand[1].suit:
                return HandEvaluator.preflop_win_percentages_suited[
                    hand[0].rank][hand[1].rank]
            else:
                return HandEvaluator.preflop_win_percentages_unsuited[
                    hand[0].rank][hand[1].rank]
        else:
            hand = map(HandEvaluator.card_to_str, hand)
            board = map(HandEvaluator.card_to_str, board)
            # Fill the rest of the board with 255s (unknown card)
            for i in xrange(5 - len(board)):
                board.append(255)
            poker_eval_result = HandEvaluator.evaluator.poker_eval(
                game="holdem",
                pockets=[hand, [255, 255]],
                dead=[],
                board=board,
                iterations=iterations)

        # Ok, we have stats. Calculate win pct, with ties as 0.5 weight
        return (poker_eval_result['eval'][0]['winhi'] + \
                0.5 * poker_eval_result['eval'][0]['tiehi']) / \
                float(poker_eval_result['info'][0])

    card_to_str = staticmethod(card_to_str)
    str_to_card = staticmethod(str_to_card)
    evaluate_hand = staticmethod(evaluate_hand)
Пример #29
0
#
# Authors:
#  Loic Dachary <*****@*****.**>
#
#

import sys
sys.path.insert(0, ".")
sys.path.insert(0, ".libs")

from pokereval import PokerEval

iterations_low = 100000
iterations_high = 200000

pokereval = PokerEval()

if pokereval.best_hand_value("hi",
                             ["Ah", "Ad", "As", "Kh", "Ks"]) != 101494784:
    sys.exit(1)

if pokereval.string2card("2h") != 0:
    sys.exit(1)

print ""
pockets = [["As", "Ad", "Ac", "Tc", "Ts", "2d", "5c"],
           ["Js", "Jc", "7s", "8c", "8d", "3c", "3h"], [255, 255]]
print "stud7 (1) result = %s\n" % pokereval.winners(
    game="7stud", pockets=pockets, dead=[], board=[])

pockets = [[22, 18, 21, 3, 41, 1, 30], [39, 255, 255, 15, 13, 17, 255]]
Пример #30
0
class PokerHandEval:
    def __init__(self):
        self.hand_groups = {
            "A": ["AA", "AKs", "KK"],
            "B": ["AK", "QQ"],
            "C": ["JJ", "TT"],
            "D": ["AQs", "AQ", "AJs", "99", "88"],
            "E": ["AJ", "ATs", "KQs", "77", "66", "55"],
            "F": ["AT", "KQ", "KJs", "QJs", "44", "33", "22"],
            "G": [
                "A9s", "A8s", "A7s", "A6s", "A5s", "A4s", "A3s", "A2s", "KTs",
                "QTs", "JTs", "J9s", "T9s", "98s"
            ],
            "H": ["KJ", "KT", "QJ", "J8s", "T8s", "87s", "76s"]
        }
        self.hand_values = {
            "A": 13,
            "K": 12,
            "Q": 11,
            "J": 10,
            "T": 9,
            "9": 8,
            "8": 7,
            "7": 6,
            "6": 5,
            "5": 4,
            "4": 3,
            "3": 2,
            "2": 1
        }
        self.odds_map = {
            "flop": {
                1: 0.045,
                2: 0.088,
                3: 0.13,
                4: 0.172,
                5: 0.212,
                6: 0.252,
                7: 0.29,
                8: 0.327,
                9: 0.364,
                10: 0.399,
                11: 0.433,
                12: 0.467,
                13: 0.499,
                14: 0.53,
                15: 0.561,
                16: 0.59,
                17: 0.618
            },
            "turn": {
                1: 0.023,
                2: 0.045,
                3: 0.68,
                4: 0.091,
                5: 0.114,
                6: 0.136,
                7: 0.159,
                8: 0.182,
                9: 0.205,
                10: 0.227,
                11: 0.25,
                12: 0.273,
                13: 0.295,
                14: 0.318,
                15: 0.341,
                16: 0.364,
                17: 0.386
            }
        }
        self.eval = PokerEval()

    def prepareHand(self, hand):
        h = hand.split(" ")
        if self.hand_values[h[1][0]] > self.hand_values[h[0][0]]:
            self.hand = "%s%s" % (h[1][0], h[0][0])
        else:
            self.hand = "%s%s" % (h[0][0], h[1][0])
        if h[0][1] == h[1][1]:
            self.hand += "s"

    def getHandGroup(self):
        for group in self.hand_groups:
            if self.hand in self.hand_groups[group]:
                return group
        return False

    def getHandValue(self, game, serial):
        hand = game.getHandAsString(serial)
        board = game.getBoardAsString()
        board_list = board.split(" ")
        if len(board_list) < 5:
            for i in range(len(board_list), 5):
                board_list.append("__")
        hand_list = hand.split(" ")
        cards = hand_list + board_list
        return self.eval.best_hand("hi", self.eval.string2card(cards), [])

    def parseHistory(self, hist):
        self.round_action = {}
        self.action2serials = {"call": [], "raise": [], "fold": []}
        self.serial2action = {}
        ret = ""
        for event in hist:
            type = event[0]
            if type in ["fold", "check", "call", "raise"]:
                if len(event) == 3:
                    (action, serial, amount) = event
                else:
                    (action, serial) = event
                    amount = False
                ret = "action: %s, serial:%d" % (action, serial)
                if amount:
                    ret += ", amount = %d" % amount
                    self.round_action[serial] = [action, amount]
                else:
                    self.round_action[serial] = [action]
                self.serial2action[serial] = action
                if action in self.action2serials.keys():
                    if not serial in self.action2serials[action]:
                        self.action2serials[action].append(serial)

    def getPosition(self, game, serial):
        me = game.serial2player[serial]
        players = game.serialsAllSorted()
        for player in players:
            user = game.serial2player[player]
        user_positions = {}
        player_seats = {}
        i = 1
        for p in game.serialsAllSorted():
            user = game.serial2player[p]
            player_seats[user.seat] = p
        max_seat = len(player_seats)
        early = max_seat / 3
        middle = early * 2
        self.my_seat = me.seat
        self.serial2position = {}
        self.position2serials = {"early": [], "middle": [], "late": []}
        for p in player_seats.keys():
            player_serial = player_seats[p]
            if i <= early:
                position = "early"
            elif i >= (early + 1) and i <= middle:
                position = "middle"
            else:
                position = "late"
            if not player_serial in self.serial2position.keys():
                self.serial2position[player_serial] = position
            if not player_serial in self.position2serials[position]:
                self.position2serials[position].append(player_serial)
            if p == self.my_seat:
                self.position = position
            i += 1
Пример #31
0
class Table(object):
    def __init__(self, protocol, avatar, table_info):
        self.protocol = protocol
        self.id = table_info.get('id', 0)
        self.seat = table_info.get('player_seated', -1)
        self.seats = [0] * table_info.get('seats', 10)
        if self.seat != -1:
            self.seats[self.seat] = avatar.serial
            assert avatar.seat == self.seat, "as %s, ss %s" % (avatar.seat, self.seat)
        self.name = table_info.get('name', 'unnamed')
        self.betting_structure =  table_info['betting_structure']
        blinds, buy_ins, limit = table_info['betting_structure'].split('_')
        min_buy_in, max_buy_in = buy_ins.split('-')
        small, big = blinds.split('-')

        self.max_buy_in = int(max_buy_in)*100
        self.min_buy_in = int(min_buy_in)*100
        self.big_blind = int(big)*100
        self.small_blind = int(small)*100

        self.players = {avatar.serial: avatar}
        self.avatar = avatar
        self._serial_and_game_id = dict(serial=avatar.serial, game_id=self.id)
        self._eval = PokerEval()
        self.reset()
        self._game_state = GAME_STATE_NULL

    def reset(self):
        """reseting game states for a new hand"""
        self.board_cards = []
        self.position = -1
        self._reset_players()

    def getBoardCards(self):
        """return a list of board games"""
        return list(map(lambda x:x&63, self.board_cards))

    def getAvatarInfo(self):
        """return a string of usefull information about the avatar"""
        return ", ".join(self._get_avatar_info())

    def isInPosition(self, serial):
        """returs true if player with serial is in position"""
        return serial in self.in_game and self.position == self.in_game.index(serial)

    def logIt(self, astr, prefix=" [D] "):
        """a little helper function to log output"""
        self.protocol.logIt(astr, prefix=prefix)

    def updateSeats(self, seats):
        """update seat information"""
        for index, (old, new) in enumerate(zip(self.seats, seats)):
            if old == 0 and new != 0:
                self.addPlayer(index, new)
            elif old != 0 and new == 0:
                self.removePlayer(index)
            elif old != new:
                self.removePlayer(index)
                self.addPlayer(index, new)
                self.logIt("warning idx %s, old %s, new %s" % (index, old, new))

    def addPlayer(self, index, serial):
        """Add player to this table"""
        self.seats[index] = serial
        # Request more information about this player
        if serial == self.avatar.serial:
            self.players[index] = self.avatar
        else:
            self.protocol.sendPacket(networkpackets.PacketPokerGetUserInfo(serial=serial))

    def removePlayer(self, index):
        """remove player from this table"""
        serial = self.seats[index]
        self.seats[index]=0
        if serial in self.players:
            del self.players[serial]

    def updatePlayer(self, player_info):
        """update general palyer information (we requested them in addPlayer)"""
        player = self._get_or_create_player(**player_info)
        player.update(player_info)

    def updatePlayerChips(self, serial, chips, bet):
        """update players chips"""
        player = self._get_or_create_player(serial=serial)
        return player.updateChips(chips, bet)

    def updatePlayerCards(self, serial, cards):
        """update players cards"""
        player = self._get_player(serial)
        player.updateCards(cards)

    def rebuy(self, serial, amount):
        """update money state of player because a rebuy happend"""
        player = self._get_player(serial)
        player.rebuy(amount)

    def _reset_players(self):
        """reset player states"""
        for player in self.players.values():
            player.reset()

    def highestBetNotFold(self):
        """returns the highest bet of all players that are not fold"""
        return max([0]+[p._bet for p in self.players.values() if p.serial in self.in_game and p.notFold()])
    
    def inSmallBlindPosition(self):
        """returns True if the player in position is in small_blind position"""
        return len(self.in_game) > 0 and ((self.dealer + 1) % len(self.in_game)) == self.position

    def bigBlind(self):
        """returns the big_blind of the current table"""
        return self.big_blind or 0

    def doBuyIn(self):
        """actually request a buy_in"""
        self.protocol.sendPacket(networkpackets.PacketPokerBuyIn(amount=self.max_buy_in, **self._serial_and_game_id))
        self.protocol.sendPacket(networkpackets.PacketPokerAutoBlindAnte(**self._serial_and_game_id))
    
    def doRebuy(self, amount):
        """actually request a rebuy"""
        self.protocol.sendPacket(networkpackets.PacketPokerRebuy(amount=amount, **self._serial_and_game_id))

    def doSit(self):
        """actually request a sit"""
        self.protocol.sendPacket(networkpackets.PacketPokerSit(**self._serial_and_game_id))
    
    def doSitOut(self):
        """actually request a sitout"""
        self.protocol.sendPacket(networkpackets.PacketPokerSitOut(**self._serial_and_game_id))
    
    def doQuit(self):
        """actually request a table quit"""
        self.protocol.sendPacket(networkpackets.PacketPokerTableQuit(**self._serial_and_game_id))
    
    def doFold(self):
        """actually request a fold"""
        self.protocol.sendPacket(networkpackets.PacketPokerFold(**self._serial_and_game_id))
    
    def doCheck(self):
        """actually request a check"""
        self.protocol.sendPacket(networkpackets.PacketPokerCheck(**self._serial_and_game_id))
    
    def doCall(self):
        """actually request a call"""
        self.protocol.sendPacket(networkpackets.PacketPokerCall(**self._serial_and_game_id))
    
    def doAllIn(self):
        """actually raise all chips"""
        self.doRaise(self.avatar.getChips())
    def doRaise(self, amount):
        """
            actually request a raise by a given amount.
            WARNING: If the amount you requested is too low, the raise will be accepted but the 
            minimum amount to raise will be used instead. You will be informend about the amount 
            that is used to raise.
        """
        self.protocol.sendPacket(networkpackets.PacketPokerRaise(amount=amount, **self._serial_and_game_id))
    

    def explain(self, packet, state):
        """packets that might be interesting for the game will be handled here"""
        def handlePacketPokerBuyInLimits(packet):
            self.max_buy_in = packet.max
            self.min_buy_in = packet.min
        def handlePacketPokerSeats(packet):
            return self.updateSeats(packet.seats)
        def handlePacketPokerPlayerInfo(packet):
            self.updatePlayer(packet.__dict__)
        def handlePacketPokerPlayerChips(packet):
            return self.updatePlayerChips(packet.serial, chips=packet.money, bet=packet.bet)
        def handlePacketPokerPlayerArrive(packet):
            self.updatePlayer(packet.__dict__)
        def handlePacketPokerPlayerLeave(packet):
            self.removePlayer(packet.seat)
        def handlePacketPokerSit(packet):
            self._get_player(packet.serial).sit()
        def handlePacketPokerSitOut(packet):
            self._get_player(packet.serial).sitOut()
        def handlePacketPokerRebuy(packet):
            assert self.id == packet.game_id
            self.rebuy(packet.serial, packet.amount)
        def handlePacketPokerInGame(packet):
            assert self.id == packet.game_id
            self.in_game = packet.players
        def handlePacketPokerPosition(packet):
            assert self.id == packet.game_id
            self.position = packet.position
        def handlePacketPokerStart(packet):
            assert self.id == packet.game_id
            self.reset()
            self.hand_serial = packet.hand_serial
        def handlePacketPokerDealer(packet):
            assert self.id == packet.game_id
            # assert self.dealer == packet.previous_dealer
            self.dealer = packet.dealer
        def handlePacketPokerPlayerCards(packet):
            self.updatePlayerCards(packet.serial, packet.cards)
            if packet.serial == self.avatar.serial:
                self.logIt("You got %r" % self._cards_to_string(packet.cards))
        def handlePacketPokerBoardCards(packet):
            self.board_cards = packet.cards
        def handlePacketPokerRaise(packet):
            self._get_player(packet.serial).bet(packet.amount)
        def handlePacketPokerCall(packet):
            player = self._get_player(packet.serial)
            highestbet = self.highestBetNotFold()
            bigb =self.bigBlind() if self._game_state == GAME_STATE_PRE_FLOP and not self.inSmallBlindPosition() else 0
            # import rpdb2; rpdb2.start_embedded_debugger("haha")
            self.logIt("%r, %r" % (highestbet,bigb))
            amount = min(
                max(highestbet,bigb) - player._bet,
                player.money
            )
            player.bet(amount)
        def handlePacketPokerState(packet):
            self._game_state = packet.string
        def handlePacketPokerBlind(packet):
            self._get_player(packet.serial).bet(packet.amount)

        try:
            handle = locals()["handle"+packet.__class__.__name__]
            return handle(packet)
        except KeyError:
            # self.logIt(" explain cant handle : %r" % packet.__class__.__name__)
            return True
        except Exception:
            exc_type, exc_value, exc_traceback = sys.exc_info()
            self.logIt(packet.__class__.__name__, prefix=" EEE  handle failed: ")

            for exline in traceback.format_exception(exc_type, exc_value,
                                          exc_traceback):
                for line in exline.split('\n'):
                    self.logIt(str(line), prefix=" EEE ")

    def _cards_to_string(self, cards):
        """return a string for cards in a human readable way"""
        return repr(self._eval.card2string(map(lambda x: x & 63, cards)))\
            #.lower().replace("h", u"\u2761").replace("s", u"\u2660").replace("c", u"\u2663").replace("d", u"\u2662")
    def _get_or_create_player(self, serial, seat=None, **player_info):
        """returns the player with the serial, the player will be created if it does not exist yet"""
        # serial = player_info['serial']
        # seat = player_info['seat']
        if seat and self.seats[seat] != 0 and serial != self.seats[seat]:
            self.logIt("%s is allready on seat %s, cleared" % (self.seats[seat], seat))
            del self.players[self.seats[seat]]
            self.seats[seat] = serial

        if serial not in self.players:
            self.players[serial] = Player(serial=serial, seat=seat, **player_info)

        return self.players[serial]
    
    def _get_player(self, serial):
        """returns the player, raises an IndexError if it does not exist"""
        return self.players[serial]

    def _log_players(self):
        """ log player informations """
        self.logIt("Players:")
        for player in self.players.itervalues():
            self.logIt(player._player_info())
        self.logIt("")

    
    def getDebugLines(self):
        """returns a list of debug lines (yellow box)"""
        return self._get_table_info() + self._get_avatar_info() + self._get_player_info()

    @catcher
    def _get_table_info(self):
        """returns a list of table informations"""
        highestbet = self.highestBetNotFold(),
        bigb =self.bigBlind() if self._game_state == GAME_STATE_PRE_FLOP and not self.inSmallBlindPosition() else 0
        return ["blinds: small:%r big:%r" % (self.small_blind, self.big_blind),
                "buy_ins: min:%r max:%r" % (self.min_buy_in, self.max_buy_in),
                "bs: %r" % self.betting_structure,
                "highestbet = %r" % highestbet,
                "bigb = %r" % bigb,]
    @catcher
    def _get_player_info(self):
        """returns a list with player informations for all players"""
        return [player._player_info() for player in self.players.values()]
    @catcher
    def _get_avatar_info(self):
        """returns informations of the avatar that is currently logged in"""
        retvals = []
        if self.avatar.cards:
            retvals.append("hand: " + self._cards_to_string(self.avatar.cards))
        if self.board_cards:
            retvals.append("board: " + self._cards_to_string(self.board_cards))
            if self.avatar.cards:
                best_hand = self._eval.best_hand("hi", self.avatar.getCards() + self.getBoardCards())
                desc = best_hand.pop(0)
                retvals.append("%s: %s" % (desc, self._cards_to_string(best_hand)))
        return retvals
Пример #32
0
    def calculate_hand_potential_without_heuristics(current_hole_cards,
                                                    board_cards, round_id,
                                                    full_deck):
        """
        Implemented as described in the page 23 of the thesis in: http://poker.cs.ualberta.ca/publications/davidson.msc.pdf
        """
        our_cards = current_hole_cards + board_cards
        out_cards_set = frozenset(our_cards)

        # hand potential array, each index represents ahead, tied, and behind
        ahead = 0
        tied = 1
        behind = 2
        hp = [[0.0, 0.0, 0.0], [0.0, 0.0, 0.0], [0.0, 0.0, 0.0]]
        hp_total = [0.0, 0.0, 0.0]
        total = 0.0
        pokereval = PokerEval()
        our_rank = pokereval.evaln(our_cards)
        # considers all two card combinations of the remaining cards for the opponent

        opponent_cards_combinations = list(itertools.combinations(
            full_deck, 2))
        indices = []
        for index, cards in enumerate(opponent_cards_combinations):
            card1, card2 = cards
            if card1 in our_cards or card2 in our_cards:
                indices.append(index)
        for index in reversed(indices):
            opponent_cards_combinations.pop(index)

        for opponent_card1, opponent_card2 in opponent_cards_combinations:
            opponent_rank = pokereval.evaln([opponent_card1] +
                                            [opponent_card2] + board_cards)
            if our_rank > opponent_rank:
                index = ahead
            elif our_rank == opponent_rank:
                index = tied
            else:
                index = behind
            # hp_total[index] += 1.0 # original version

            # all possible board cards to come
            deck = list(full_deck)
            dealt_card = current_hole_cards + board_cards + [
                opponent_card1
            ] + [opponent_card2]
            deck_without_dealt_cards = [
                card for card in deck if card not in dealt_card
            ]
            if round_id == 1:  # flop
                cards_combinations = list(
                    itertools.combinations(deck_without_dealt_cards, 2))
                # cards_combinations = random.sample(cards_combinations, int(len(cards_combinations)*0.2))
                for turn, river in cards_combinations:
                    # final 5-card board
                    board = board_cards + [turn] + [river]
                    our_future_rank = pokereval.evaln(current_hole_cards +
                                                      board)
                    opponent_future_rank = pokereval.evaln([opponent_card1] +
                                                           [opponent_card2] +
                                                           board)
                    if our_future_rank > opponent_future_rank:
                        hp[index][ahead] += 1.0
                    elif our_future_rank == opponent_future_rank:
                        hp[index][tied] += 1.0
                    else:
                        hp[index][behind] += 1.0
                    total += 1.0
                    hp_total[index] += 1.0  # new version
            else:  # turn
                # cards = random.sample(deck_without_dealt_cards, int(len(deck_without_dealt_cards)*0.75))
                cards = deck_without_dealt_cards
                for river in cards:
                    # final 5-card board
                    board = board_cards + [river]
                    our_future_rank = pokereval.evaln(current_hole_cards +
                                                      board)
                    opponent_future_rank = pokereval.evaln([opponent_card1] +
                                                           [opponent_card2] +
                                                           board)
                    if our_future_rank > opponent_future_rank:
                        hp[index][ahead] += 1.0
                    elif our_future_rank == opponent_future_rank:
                        hp[index][tied] += 1.0
                    else:
                        hp[index][behind] += 1.0
                    total += 1.0
                    hp_total[index] += 1.0  # new version

        # the original formula:
        # ppot = (hp[behind][ahead] + hp[behind][tied]/2.0 + hp[tied][ahead]/2.0) / (hp_total[behind] + hp_total[tied]/2.0)
        # npot = (hp[ahead][behind] + hp[tied][behind]/2.0 + hp[ahead][tied]/2.0) / (hp_total[ahead] + hp_total[tied]/2.0)

        # ppot: were behind but moved ahead: cant use the original hp_total, because the result isnt normalzied and because it dont work for the heuristics
        # added hp[ahead][ahead] so already good hands wouldnt be given a below average potential
        ppot = (hp[ahead][ahead] + hp[behind][ahead] + hp[behind][tied] / 2.0 +
                hp[tied][ahead]) / (hp_total[behind] * 1.5 + hp_total[tied] *
                                    1.0 + hp_total[ahead] * 1.0)

        # npot: were ahead but fell behind
        # npot = ((hp[ahead][behind]/total)*2.0 + (hp[ahead][tied]/total)*1.0 + (hp[tied][behind]/total)*1.0)/4.0

        return ppot
Пример #33
0
 def __init__(self, had_values, hand, board):
     self.eval = PokerEval()
     self.hand_values = {"A":13,"K":12,"Q":11,"J":10, "T":9,"9":8,"8":7,"7":6,"6":5,"5":4,"4":3,"3":2,"2":1}
     self.hand = hand
     self.board = board
Пример #34
0
'''
Created on 11 mai 2012

@author: Askylh
'''

from pokereval import PokerEval


Peval = PokerEval()
iteration=100000
ev = Peval.poker_eval(game='holdem', pockets=[["tc", "ts"], ["kd", "ad"]], board=["__", "__", "__", "__", "__"], iterations=iteration)

print ev['eval']
Пример #35
0
#
# Authors:
#  Loic Dachary <*****@*****.**>
#
#
import sys

sys.path.insert(0, ".")
sys.path.insert(0, ".libs")

from pokereval import PokerEval

iterations_low = 100000
iterations_high = 200000

pokereval = PokerEval()

if pokereval.best_hand_value("hi", ["Ah", "Ad", "As", "Kh", "Ks"]) != 101494784:
    sys.exit(1)

if pokereval.string2card("2h") != 0:
    sys.exit(1)

print ""
pockets = [["As", "Ad", "Ac", "Tc", "Ts", "2d", "5c"], ["Js", "Jc", "7s", "8c", "8d", "3c", "3h"], [255, 255]]
print "stud7 (1) result = %s\n" % pokereval.winners(game="7stud", pockets=pockets, dead=[], board=[])

pockets = [[22, 18, 21, 3, 41, 1, 30], [39, 255, 255, 15, 13, 17, 255]]
print "stud7 (2) result = %s\n" % pokereval.winners(game="7stud", pockets=pockets, dead=[], board=[])

print [j + i + "/%d" % pokereval.string2card(j + i) for i in "hdcs" for j in "23456789TJQKA"]
    def calculate_hand_potential_without_heuristics(current_hole_cards, board_cards, round_id, full_deck):
        """
        Implemented as described in the page 23 of the thesis in: http://poker.cs.ualberta.ca/publications/davidson.msc.pdf
        """
        our_cards = current_hole_cards + board_cards
        out_cards_set = frozenset(our_cards)

        # hand potential array, each index represents ahead, tied, and behind
        ahead = 0
        tied = 1
        behind = 2
        hp = [[0.0, 0.0, 0.0], [0.0, 0.0, 0.0], [0.0, 0.0, 0.0]]
        hp_total = [0.0, 0.0, 0.0]
        total = 0.0
        pokereval = PokerEval()
        our_rank = pokereval.evaln(our_cards)
        # considers all two card combinations of the remaining cards for the opponent

        opponent_cards_combinations = list(itertools.combinations(full_deck, 2))
        indices = []
        for index, cards in enumerate(opponent_cards_combinations):
            card1, card2 = cards
            if card1 in our_cards or card2 in our_cards:
                indices.append(index)
        for index in reversed(indices):
            opponent_cards_combinations.pop(index)

        for opponent_card1, opponent_card2 in opponent_cards_combinations:
            opponent_rank = pokereval.evaln([opponent_card1] + [opponent_card2] + board_cards)
            if our_rank > opponent_rank:
                index = ahead
            elif our_rank == opponent_rank:
                index = tied
            else:
                index = behind
            # hp_total[index] += 1.0 # original version

            # all possible board cards to come
            deck = list(full_deck)
            dealt_card = current_hole_cards + board_cards + [opponent_card1] + [opponent_card2]
            deck_without_dealt_cards = [card for card in deck if card not in dealt_card]
            if round_id == 1: # flop
                cards_combinations = list(itertools.combinations(deck_without_dealt_cards, 2))
                # cards_combinations = random.sample(cards_combinations, int(len(cards_combinations)*0.2))
                for turn, river in cards_combinations:
                    # final 5-card board
                    board = board_cards + [turn] + [river]
                    our_future_rank = pokereval.evaln(current_hole_cards + board)
                    opponent_future_rank = pokereval.evaln([opponent_card1] + [opponent_card2] + board)
                    if our_future_rank > opponent_future_rank:
                        hp[index][ahead] += 1.0
                    elif our_future_rank == opponent_future_rank:
                        hp[index][tied] += 1.0
                    else:
                        hp[index][behind] += 1.0
                    total += 1.0
                    hp_total[index] += 1.0 # new version
            else: # turn
                # cards = random.sample(deck_without_dealt_cards, int(len(deck_without_dealt_cards)*0.75))
                cards = deck_without_dealt_cards
                for river in cards:
                    # final 5-card board
                    board = board_cards + [river]
                    our_future_rank = pokereval.evaln(current_hole_cards + board)
                    opponent_future_rank = pokereval.evaln([opponent_card1] + [opponent_card2] + board)
                    if our_future_rank > opponent_future_rank:
                        hp[index][ahead] += 1.0
                    elif our_future_rank == opponent_future_rank:
                        hp[index][tied] += 1.0
                    else:
                        hp[index][behind] += 1.0
                    total += 1.0
                    hp_total[index] += 1.0 # new version

        # the original formula:
        # ppot = (hp[behind][ahead] + hp[behind][tied]/2.0 + hp[tied][ahead]/2.0) / (hp_total[behind] + hp_total[tied]/2.0)
        # npot = (hp[ahead][behind] + hp[tied][behind]/2.0 + hp[ahead][tied]/2.0) / (hp_total[ahead] + hp_total[tied]/2.0)

        # ppot: were behind but moved ahead: cant use the original hp_total, because the result isnt normalzied and because it dont work for the heuristics
        # added hp[ahead][ahead] so already good hands wouldnt be given a below average potential
        ppot = (hp[ahead][ahead] + hp[behind][ahead] + hp[behind][tied]/2.0 + hp[tied][ahead]) / (hp_total[behind]*1.5 + hp_total[tied]*1.0 + hp_total[ahead]*1.0)

        # npot: were ahead but fell behind
        # npot = ((hp[ahead][behind]/total)*2.0 + (hp[ahead][tied]/total)*1.0 + (hp[tied][behind]/total)*1.0)/4.0

        return ppot
Пример #37
0
		(727,207)
	)
)

op_card_pos = (
	(187,120),
	(112,211),
	(182,284),
	(598,285),
	(682,212),
	(608,122)
)

once = True
i = 1
pokereval = PokerEval()
while (once or loop):

	board=list()
	pocket=list()

	#Get screenshot of whole table
	w = gtk.gdk.get_default_root_window()
	screen = gtk.gdk.Pixbuf(gtk.gdk.COLORSPACE_RGB,False,8,795,548)
	screen = screen.get_from_drawable(w,w.get_colormap(),0,48,0,0,795,548) #src_x,src_y,dest_x,dest_y,width,height

	#Get Community Cards
	for p in comm_cards_pos: 
		card = card_at_pos(p,screen)
		if card != None: board.append(card)
Пример #38
0
class MatchHistory:
    def __init__(self, pname):
        self.history = [{}, {}, {}, {}]
        for a in range(4):  # [BET,CALL,CHECK,RAISE]:
            for s in range(4):
                self.history[s][a] = []

        self.pname = pname
        self.pokereval = PokerEval()
        self.showStats = {}

    def reset(self):
        return

    def update(self, game):
        self.showStats = []

        for action in game.hand.actions:
            if action.type == SHOW and action.player == self.pname:
                self.showStats = [[action.showCard1, action.showCard2], [0, 0]]

        if len(self.showStats) > 0:
            self.computeNewEntries(game)

    def computeNewEntries(self, game):
        playerHand = self.showStats[0]
        ev2 = TwoPocketLookup.evalPocket(Card(playerHand[0]), Card(playerHand[1]))
        ev3 = ThreePocketLookup.evalPocket(Card(playerHand[0]), Card(playerHand[1]))
        self.showStats[1] = [ev2, ev3]

        street = 0
        b = [255] * 5
        for action in game.hand.actions:
            if action.type == DEAL:
                street += 1
                if street == FLOP:  # FLOP
                    b[:3] = game.boardCards[:3]
                elif street == TURN:  # TURN
                    b[:4] = game.boardCards[:4]
                elif street == RIVER:  # RIVER
                    b = game.boardCards
                playerHand = self.showStats[0]
                pockets = [playerHand, [255, 255], [255, 255]]
                ev3 = self.pokereval.poker_eval(
                    game="holdem", pockets=pockets, dead=[], board=b, iterations=ITERATIONS
                )["eval"][0]["ev"]
                ev2 = self.pokereval.poker_eval(
                    game="holdem", pockets=pockets[:2], dead=[], board=b, iterations=ITERATIONS
                )["eval"][0]["ev"]
                self.showStats[1] = [ev2, ev3]
            elif action.player == self.pname and action.type != POST and action.type in game.hand.trackedActions:
                act = action.copy()
                act.ev = self.showStats[1]
                self.history[street][action.type].append(act)

    def __repr__(self):
        ret = "MATCH HISTORY\n"
        ret += "PLAYER " + self.pname + "\n"
        for s in range(4):
            ret += "    STREET " + str(s) + "\n"
            for a in self.history[s].keys():
                ret += "        ACTION " + ACTION_TYPES[a] + "\n"
                for i in range(len(self.history[s][a])):
                    act = self.history[s][a][i]
                    ret += "             ["
                    ret += "TYPE: " + ACTION_TYPES[act.type] + ", "
                    ret += "AMOUNT: " + str(act.amount) + ", "
                    ret += "POT AMOUNT: " + str(act.potAmount) + ", "
                    ret += "BET AMOUNT: " + str(act.betAmount) + ", "
                    ret += "EV: " + str(act.ev[0]) + " " + str(act.ev[1]) + " ]\n"
        return ret[:-1]

    def averageStrength(self, game, action, amountType):
        sum = 0
        sum2 = 0
        numMatches = 0
        amountDiffs = []  # list of action values [(action, actionAmount, abs(amount-actionAmount)
        diffBound = max(7, 0.15 * action.amount)

        # print self.history.keys() ##Need to comment out
        if action.type not in self.history[action.street].keys():
            #            print "ACTION TYPE IN AVERAGE STRENGTH", action.type
            return [-1, 1000]
        actions = self.history[action.street][action.type]
        for a in actions:
            ev = a.ev[game.activePlayers - 2]
            if amountType == POTAMOUNT:
                if a.potAmount == action.potAmount:
                    sum += ev
                    sum2 += ev * ev
                    numMatches += 1
                else:
                    amountDiffs += [(a, a.potAmount, abs(a.potAmount - action.potAmount))]
            elif amountType == BETAMOUNT:
                if a.betAmount == action.betAmount:
                    sum += ev
                    sum2 += ev * ev
                    numMatches += 1
                else:
                    amountDiffs += [(a, a.betAmount, abs(a.betAmount - action.betAmount))]
            else:
                if a.amount == action.amount:
                    sum += ev
                    numMatches += 1
                    sum2 += ev * ev
                else:
                    diff = abs(a.amount - action.amount)
                    # only use actions within a certain range to calculate average/std values
                    if diff <= diffBound:
                        amountDiffs += [(a, a.amount, diff)]

        if numMatches < 3:
            # sort the amountDiffs by the difference in amount from the desired amount
            amountDiffs = sorted(amountDiffs, key=lambda x: x[2])
            minDiff = 0
            for amt in amountDiffs:
                ev = amt[0].ev[game.activePlayers - 2]
                if amt[2] != minDiff:
                    minDiff = amt[2]
                    if numMatches >= 3:
                        mean = float(sum) / numMatches
                        std = sqrt((sum2 * numMatches - (sum * sum)) / float(numMatches * (numMatches - 1)))
                        return [mean, std]
                sum += ev
                numMatches += 1
                sum2 += ev * ev

            return [-1, 1000]

        mean = float(sum) / numMatches
        std = sqrt((sum2 * numMatches - (sum * sum)) / float(numMatches * (numMatches - 1)))
        return [mean, std]
Пример #39
0
#  Loic Dachary <*****@*****.**>
#  Henry Precheur <*****@*****.**> (2004)
#

import unittest, sys
from os import path

TESTS_PATH = path.dirname(path.realpath(__file__))
sys.path.insert(0, path.join(TESTS_PATH, ".."))

from pokereval import PokerEval
from pokerengine import pokergame
from pokerengine.pokergame import PokerGameServer
from pokerengine.pokercards import PokerCards

poker_eval = PokerEval()
_initial_money = 1000

class TestAllIn(unittest.TestCase):

    def setUp(self, variant, betting):
        self.game = PokerGameServer("poker.%s.xml", [path.join(TESTS_PATH, '../conf')])
        self.game.setVariant(variant)
        self.game.setBettingStructure(betting)

    def bestWithStrings(self, side, serial):
        (value, cards) = self.game.bestHand(side, serial)
        return (cards[0], self.game.eval.card2string(cards[1:]))
        
    def tearDown(self):
        del self.game
Пример #40
0
class TheBostonDerbyOld:
    def __init__(self):
        """This is a very simple player that demonstrates the API and is a good
        template for getting started
        """
        # my name
        self.name = "theBostonDerby"

        self.reset(False,[])
        # game state variables -- these are updated by the engine which
        # own internal representation. so if you modify them, they'll just
        # be reset. we recommend leaving their init as is
        self.hand = None
        self.stack = None
        self.pip = None
        self.button = None
        self.opponent = None
        self.bb = None
        self.sb = None
        self.hands_played = None
        self.last_hand = 0
        self.board = None
        self.legal = None
        self.actions = None
        self.last = None
        self.pot = None
        self.ev_calc = PokerEval()
        self.ev = 0
        self.bound = 0
        self.bot = BaseBot()
        self.LOW = .02
        self.MID = .08
        self.HIGH = .15

    def reset(self, won, last_hand):
        """Reset accepts a boolean indicating whether you won a match and
        provides the last hand if you want to update any statistics from it
        """
        self.my_stats = {   'hands':0,
                            '^VPIP':[0,0,0,0],
                            'VPIP':[0,0,0,0],  # amount voluntarily placed in pot
                            '^INCR':[0,0,0,0],
                            'INCR':[0,0,0,0],   # frequency of raises
                            '^AF':0,
                            '_AF':0,
                            'AF':0,    # aggression frequency = (bets + raises)/(checks + calls)
                            #pre flop
                            '^ST':0,
                            'ST':0,    # steals = how often he raises when has first action
                            '^LMP':0,
                            'LMP':0,  # how often opponent calls
                            '_3B':0,
                            '^FBB':0,
                            'FBB':0,    # how often, after small blind raises, big blind folds
                            '^3B':0,
                            '3B':0,    # how often, after small blind raises, big blind raises
                            '_4B':0,
                            '^F3B':0,
                            'F3B':0,   # how often, after small blind raises and then big blind raises, small blind folds
                            '^4B':0,
                            '4B':0,    # how often, the small bind raises in above circumstances
                            '_F4B':0,
                            '^F4B':0,
                            'F4B':0,    #how often big blind folds to 4B
                            #flop
                            '_COB':0,
                            '^COB':0,
                            'COB':0,    # continuation bet = how often betting after betting/raising on preflop
                            '_FCOB':0,
                            '^FCOB':0,
                            'FCOB':0,   # how often opp folds to a continuation bet
                            #turn
                            '_2COB':0,
                            '^2COB':0,
                            '2COB':0,   # how often opp cb twice, once on flop and once on turn
                            '_F2COB':0,
                            '^F2COB':0,
                            'F2COB':0,  # how often opp folds to 2nd continuation bet.
                            '_CHBR':[0,0,0,0],
                            '^CHBR':[0,0,0,0],
                            'CHBR':[0,0,0,0],    # how often opp check raises
                         }
                     
        self.opp_stats = self.my_stats.copy()
        self.opp_stats['^VPIP'] = [0,0,0,0]
        self.opp_stats['VPIP'] = [0,0,0,0]
        self.opp_stats['^INCR'] = [0,0,0,0]
        self.opp_stats['INCR'] = [0,0,0,0]
        self.opp_stats['_CHBR'] = [0,0,0,0]
        self.opp_stats['^CHBR'] = [0,0,0,0]
        self.opp_stats['CHBR'] = [0,0,0,0]
        self.last = None
        self.opp_hand = 100.0
        self.cory_stats = {'A':0, 'W':0, 'C':0}

    def card2str(self, c):
        return c.__str__()

    def calculate_ev(self):
        #print self.board
        if not self.board.flop():
            suited = self.hand[0].suit != self.hand[1].suit #0 means suited, 1 means not
            if self.hand[0].rank > self.hand[1].rank:
                card_2,card_1 = self.hand
            else:
                card_1,card_2 = self.hand
            #print "looking up (%d,%d,%d)" % (card_1.rank-2,card_2.rank-card_1.rank,suited)
            ev = 100.0 - lookuphand[card_1.rank-2][card_2.rank-card_1.rank][suited]
        else:
            board = [self.card2str(c) for c in self.board.flop()]
            my_hand = [self.card2str(c) for c in self.hand]
            dead = my_hand
            if self.board.river():
                board += [self.card2str(self.board.turn()), self.card2str(self.board.river())]
                dead += board[:]
            elif self.board.turn():
                board += [self.card2str(self.board.turn()), '__']
                dead += board[:-1]
            else:
                board += ['__','__']
                dead += board[:-2]
            if self.opp_hand == 100.0:
                ev = self.ev_calc.poker_eval(game="holdem",pockets=[[self.card2str(c) for c in self.hand],['__','__']],dead=[],board=board,iterations=1000)
                ev = ev['eval'][0]['ev']/10.0
            else:
                hands = reduce(lambda x,y:x+y, lookupvalue[:int(self.opp_hand*10)])
                wins = 0
                iters = 30
                num_hands = 0
                for hand in hands:
                    if hand[0] in dead or hand[1] in dead: continue
                    ev = self.ev_calc.poker_eval(game="holdem",pockets=[my_hand,list(hand)],dead=[],board=board,iterations=iters)
                    wins += ev['eval'][0]['winhi']+ev['eval'][0]['tiehi']/2.0
                    num_hands += 1
                ev = wins/float(num_hands*iters)
        self.ev = ev/100.0
    
    def hand_confidence(self):
        stack_size = self.stack + self.pip
        self.bound = stack_size
        if not self.board.flop():
            if stack_size < 30*self.bb:
                if self.ev < .7: #if small stack, and not one of best hands
                    self.bound = 0 # fold
                else:
                    self.bound = -1
            else:
                if self.ev > .9:# or (self.stats['pfhb'] > 0.25 and self.hands_played > 12):
                    self.bound = stack_size
                elif self.ev > .8:
                    self.bound = int(.1 * stack_size)
                elif self.ev > .5:
                    self.bound = 2 * self.bb
                else:
                    self.bound = self.bb
        else:
            if self.ev < .33:
                self.bound = min(int(max(self.pot*self.ev/(1-3*self.ev),0)),stack_size)

    def classify(self, act):
        action = None
        if isinstance(act, Post):
            action = POST
        elif isinstance(act, Check): 
            action = CHECK
        elif isinstance(act, Bet):
            action = BET
        elif isinstance(act, Raise): 
            action = RAISE
        elif isinstance(act, Fold): 
            action = FOLD
        elif isinstance(act, Call): 
            action = CALL
        elif isinstance(act, Show):
            action = SHOW
        elif isinstance(act, Deal): 
            action = DEAL
        elif isinstance(act, Won): 
            action = WON
        else :
            print "umm, unknown action taken!", act
        return action
        
    def calculate_stats(self,last):
        #parse all actions in previous hand into useful information
        if DEBUG: print "calculating stats for hand: ", last
        tallies = {'raises':0, 'bets':0, 'folds':0, 'calls':0, 'checks':0}
        my_actions = dict(zip(range(4),[tallies.copy() for x in range(4)]))
        opp_actions = dict(zip(range(4),[tallies.copy() for x in range(4)]))
        hand = deque(last[:])
        act = hand.popleft() #first action is always sb posting their blind
        my_actions['position'] = act[0] == self.name #position = 1 means sb, 0 means BB
        opp_actions['position'] = not my_actions['position'] #if i'm not small blind, opp must be
        act = hand.pop()
        my_actions['won'] = act[0] == self.name
        opp_actions['won'] = not my_actions['won']
        this_hand = {self.name:my_actions, self.opponent['name']:opp_actions, 'steal':False, 'limp':False}
        hand.popleft() # second action is always bb posting, and is useless

        street = 0 #0 is preflop, 1 is flop, 2 is turn and 3 is river 
        first = True
        while len(hand) > 0 :
            act = hand.popleft()
            if act[0] == 'Dealer': #then this action corresponds to changing street
                street += 1
                continue
            action = self.classify(act[1])
            if first:   
                first = False
                if action == RAISE:
                    this_hand['steal'] = True
                elif action == CALL:
                    this_hand['limp'] = True

            if act[0] in [self.name, self.opponent['name']]:
                if action == RAISE:
                    this_hand[act[0]][street]['raises'] += 1
                elif action == CHECK:
                    this_hand[act[0]][street]['checks'] += 1
                elif action == CALL:
                    this_hand[act[0]][street]['calls'] += 1
                elif action == FOLD:
                    this_hand[act[0]][street]['folds'] += 1
                elif action == BET:
                    this_hand[act[0]][street]['bets'] += 1
            else:
                print "unknown player: ",act[0]

        self.my_stats['hands'] += 1
        self.opp_stats['hands'] += 1

        self.update_stats(self.opp_stats, my_actions, opp_actions, this_hand['steal'], this_hand['limp'])
        self.update_stats(self.my_stats, opp_actions, my_actions, this_hand['steal'], this_hand['limp'])
        
        self.calc_cory(self.cory_stats, my_actions, opp_actions, this_hand['steal'], this_hand['limp'])
        
        if opp_actions['won']:
            hand = last[:]
            act = hand.pop()
            while act[0] != self.opponent['name']:
                act= hand.pop()
            action = self.classify(act[1])
            if action == RAISE:
                self.cory_stats['A'] += 20
            elif action == BET or action == CALL:
                if action.amount == self.opponent['stack']+self.opponent['pip']:
                    self.cory_stats['A'] += 10
                else:   
                    self.cory_stats['C'] += 20
            
    def calc_cory(self, stats, me, opp, steal, limp):
        stats['A'] += 5*sum([opp[x][y] for x in range(4) for y in ['bets', 'raises']])
        stats['A'] += 10*sum([opp[x]['raises']-1 for x in range(4)])
        stats['C'] += 5*sum([opp[x][y] for x in range(4) for y in ['bets', 'raises', 'calls']])
        stats['C'] += 10*sum([opp[x]['calls']>0 for x in range(4) if opp[x]['raises']>0])
        stats['W'] += 5*(limp and opp['position'])
        stats['W'] += 3*(opp[PREFLOP]['folds']>0)
        stats['W'] += 5*(sum([opp[x]['folds'] for x in [FLOP,TURN,RIVER]])>0)
        stats['A'] += 20*sum([1 for x in [FLOP,TURN,RIVER] if opp[x]['checks']>0 and me[x]['bets'] >0 and opp[x]['raises']>0])

    def update_stats(self,stats,me,opp,steal,limp):
        this_hand = {}
        for street in range(4):
            if opp[street]['raises'] or opp[street]['bets'] or opp[street]['calls']:
                stats['^VPIP'][street] += 1
            if opp[street]['raises']:
                stats['^INCR'][street] += 1
            stats['VPIP'][street] = stats['^VPIP'][street]/float(stats['hands'])
            stats['INCR'][street] = stats['^INCR'][street]/float(stats['hands'])
        this_hand['^AF'] = sum([opp[x]['raises'] + opp[x]['bets'] for x in [FLOP, TURN, RIVER]])
        this_hand['_AF'] = sum([opp[x]['calls'] for x in [FLOP, TURN, RIVER]])
        
        #PREFLOP
        this_hand['^ST'] = steal and opp['position']
        this_hand['^LMP']= limp and opp['position']
        this_hand['_3B'] = steal and not opp['position']
        this_hand['^FBB']= this_hand['_3B'] and opp[0]['folds'] and opp[0]['raises'] == 0
        this_hand['^3B'] = this_hand['_3B'] and opp[0]['raises'] > 0
        this_hand['_4B'] = this_hand['^ST'] and me[0]['raises'] > 0
        this_hand['^F3B']= this_hand['_4B'] and opp[0]['folds'] and opp[0]['raises'] == 1
        this_hand['^4B'] = this_hand['_4B'] and opp[0]['raises'] >= 2
        this_hand['_F4B']= this_hand['^3B'] and me[0]['raises'] >= 2
        this_hand['^F4B']= this_hand['_F4B']and opp[0]['folds'] and opp[0]['raises'] == 1
        
        #FLOP
        this_hand['_COB'] = opp['position'] and opp[0]['raises'] > 0 and me[0]['calls']>0 and me[1]['checks']>0
        this_hand['^COB'] = this_hand['_COB'] and opp[1]['bets'] > 0
        this_hand['_FCOB']= not opp['position'] and me[0]['raises']>0 and opp[0]['calls']>0 and opp[1]['checks']>0 and me[1]['bets']>0
        this_hand['^FCOB']= this_hand['_FCOB'] and opp[1]['folds']>0

        #TURN
        this_hand['_2COB'] = this_hand['^COB'] and me[2]['checks']>0
        this_hand['^2COB'] = this_hand['_2COB'] and opp[2]['bets']>0
        this_hand['_F2COB']= this_hand['_FCOB'] and me[2]['bets']>0
        this_hand['^F2COB']= this_hand['_F2COB'] and opp[2]['folds']>0
        
        this_hand['_CHBR'] = [0,0,0,0]
        this_hand['^CHBR'] = [0,0,0,0]
        
        #POSTFLOP
        for street in [FLOP, TURN, RIVER]:
            this_hand['_CHBR'][street] = opp[street]['checks']>0 and me[street]['bets'] >0
            this_hand['^CHBR'][street] = this_hand['_CHBR'][street] and opp[street]['raises']>0
        
        for stat in stats.keys():
            if this_hand.has_key(stat) and isinstance(this_hand[stat],int):
                stats[stat] += this_hand[stat]
        stats['AF'] = stats['^AF']/float(stats['_AF']) if stats['_AF'] else None
        stats['ST'] = stats['^ST']/float(stats['hands'])
        stats['LMP'] = stats['^LMP']/float(stats['hands'])
        stats['FBB'] = stats['^FBB']/float(stats['_3B']) if stats['_3B'] else None
        stats['3B'] = stats['^3B']/float(stats['_3B']) if stats['_3B'] else None
        stats['F3B'] = stats['^F3B']/float(stats['_4B']) if stats['_4B'] else None
        stats['4B'] = stats['^4B']/float(stats['_4B']) if stats['_4B'] else None
        stats['F4B'] = stats['^F4B']/float(stats['_F4B']) if stats['_F4B'] else None
        stats['COB'] = stats['^COB']/float(stats['_COB']) if stats['_COB'] else None
        stats['FCOB'] = stats['^FCOB']/float(stats['_FCOB']) if stats['_FCOB'] else None
        stats['2COB'] = stats['^2COB']/float(stats['_2COB']) if stats['_2COB'] else None
        stats['F2COB'] = stats['^F2COB']/float(stats['_F2COB']) if stats['_F2COB'] else None
        for street in [FLOP, TURN, RIVER]:
            stats['_CHBR'][street] += this_hand['_CHBR'][street]
            stats['^CHBR'][street] += this_hand['^CHBR'][street]
            stats['CHBR'][street] = stats['^CHBR'][street]/float(stats['_CHBR'][street]) if stats['_CHBR'][street] else None

    def respond(self):
        if DEBUG: print self.name
        if DEBUG: print self.hands_played, self.last_hand, self.hand, self.board
        if DEBUG: print self.actions, self.opponent
        self.calculate_ev()
        self.hand_confidence()
        if DEBUG: print "ev=%d, pot=%d, bound=%d" % (self.ev*100, self.pot, self.bound)
        if self.hands_played != self.last_hand and self.hands_played:
            if self.hands_played == self.last_hand + 2: #if we missed one
                self.calculate_stats(self.last[0])
            self.calculate_stats(self.last[1])
            self.last_hand = self.hands_played
            self.bot.new_hand() #notify our bot of new hand
            if DEBUG: print self.opp_stats
            if DEBUG: raw_input()
        if self.board.flop():
            last_act = self.actions[-1]
            last_action = self.classify(last_act[1])
            if last_action == BET:
                if last_act[1].amount < .5*self.pot:
                    self.cory_stats['W'] += 5
                elif last_act[1].amount > self.pot:
                    self.cory_stats['A'] += 10
                if self.button: #he's BB
                    self.cory_stats['A'] += 5
        action = self.bot.respond(self)
        return action