Skip to content

Commit

Permalink
Add test cases, make test cases pass in python3
Browse files Browse the repository at this point in the history
  • Loading branch information
julianandrews committed Sep 19, 2015
1 parent e2fba51 commit a74c859
Show file tree
Hide file tree
Showing 3 changed files with 150 additions and 26 deletions.
15 changes: 9 additions & 6 deletions eval7/range_string.py
Original file line number Diff line number Diff line change
Expand Up @@ -193,9 +193,9 @@ def weight_to_float(w):


def expand_hand_type_group(htg):
"""Take a hand type grouping such as ATs+ or K8o-KJo and return a list of
hand type tokens. e.g.:
ATs-AQs -> ["ATs", "AJs", "AQs"]
"""Take a parsed hand type grouping such as ('ATs', '+') or
('K8o', '-', 'KJo') and return a list of hand type tokens. e.g.:
('ATs', '-', 'AQs') -> ["ATs", "AJs", "AQs"]
"""
tokens = []

Expand Down Expand Up @@ -252,10 +252,12 @@ def sorted_ranks(token):

def normalize_token(token):
if token[0] == '#':
# Comment
normalized = token
elif len(token) == 4:
rs = map(ranks.index, [token[0].upper(), token[2].upper()])
suit_ranks = map(suits.index, [token[1], token[3]])
# Single hand (e.g.: 7c3d)
rs = [ranks.index(x) for x in (token[0].upper(), token[2].upper())]
suit_ranks = [suits.index(x) for x in (token[1], token[3])]
if rs[0] == rs[1] and suit_ranks[0] == suit_ranks[1]:
raise RangeStringError("Invalid Token: {}".format(token))
if rs[0] < rs[1] or \
Expand All @@ -264,8 +266,9 @@ def normalize_token(token):
else:
normalized = token
else:
# Normal token (e.g.: 22, ATs, KQ)
rs = sorted(
map(lambda x: ranks.index(x.upper()), token[:2]),
[ranks.index(x.upper()) for x in token[:2]],
reverse=True
)
normalized = ''.join(ranks[i] for i in rs) + token_suitedness(token)
Expand Down
34 changes: 14 additions & 20 deletions eval7/test_eval7.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
class TestEval7(unittest.TestCase):
def test_hand_to_mask(self):
# Highest and lowest cards
cards = map(eval7.Card, ["As", "2c"])
cards = [eval7.Card(x) for x in ("As", "2c")]
result = cards[0].mask | cards[1].mask
self.assertEqual(result, 2251799813685249)

Expand All @@ -29,30 +29,24 @@ def test_evaluate(self):
(['3c', '2c', '5c', 'Ac', '4c', 'Kd', 'Kc'], 134414336, 'Straight Flush'),
)
for card_strs, expected_val, expected_type in cases:
cards = map(eval7.Card, card_strs)
cards = tuple(map(eval7.Card, card_strs))
value = eval7.evaluate(cards)
hand_type = eval7.hand_type(value)
self.assertEqual(value, expected_val)
self.assertEqual(hand_type, expected_type)

def test_hand_vs_range_exact(self):
hand = map(eval7.Card, ("Ac", "Ah"))
villain = eval7.HandRange("AA")
board = map(eval7.Card, ("Kh", "Jd", "8c", "5d", "2s"))
equity = eval7.py_hand_vs_range_exact(hand, villain, board)
self.assertEqual(equity, 0.5)

hand = map(eval7.Card, ("Ac", "Ah"))
villain = eval7.HandRange("AsAd")
board = map(eval7.Card, ("Kh", "Jd", "8c", "5d", "2s"))
equity = eval7.py_hand_vs_range_exact(hand, villain, board)
self.assertEqual(equity, 0.5)

hand = map(eval7.Card, ("As", "Ad"))
villain = eval7.HandRange("AA, A3o, 32s")
board = map(eval7.Card, ("Kh", "Jd", "8c", "5d", "2s"))
equity = eval7.py_hand_vs_range_exact(hand, villain, board)
self.assertAlmostEqual(equity, 0.95, places=7)
cases = (
(("Ac", "Ah"), "AA", ("Kh", "Jd", "8c", "5d", "2s"), 0.5),
(("Ac", "Ah"), "AsAd", ("Kh", "Jd", "8c", "5d", "2s"), 0.5),
(("As", "Ad"), "AA, A3o, 32s", ("Kh", "Jd", "8c", "5d", "2s"), 0.95),
)
for hand_strs, range_str, board_strs, expected_equity in cases:
hand = tuple(map(eval7.Card, hand_strs))
villain = eval7.HandRange(range_str)
board = tuple(map(eval7.Card, board_strs))
equity = eval7.py_hand_vs_range_exact(hand, villain, board)
self.assertAlmostEqual(equity, expected_equity, places=7)

def test_hand_vs_range_monte_carlo(self):
hand = map(eval7.Card, ("As", "Ad"))
Expand All @@ -77,7 +71,7 @@ def test_all_hands_vs_range(self):
# Hero has an impossible hand in his range.
hero = eval7.HandRange("JsJc,QsJs")
villain = eval7.HandRange("JJ")
board = map(eval7.Card, ("Kh", "Jd", "8c"))
board = tuple(map(eval7.Card, ("Kh", "Jd", "8c")))
equity_map = eval7.py_all_hands_vs_range(hero, villain, board, 10000000)
hand = tuple(map(eval7.Card, ("Qs", "Js")))
self.assertAlmostEqual(equity_map[hand], 0.03687, delta=0.0002)
Expand Down
127 changes: 127 additions & 0 deletions eval7/test_range_string.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
# Copyright 2014 Julian Andrews
#
# This software may be modified and distributed under the terms
# of the MIT license. See the LICENSE file for details.

from __future__ import absolute_import

import unittest

from eval7 import range_string


class RangeStringTestCase(unittest.TestCase):
@unittest.skip('Unimplemented test')
def test_string_to_hands(self):
pass

@unittest.skip('Unimplemented test')
def test_tokens_to_string(self):
pass

@unittest.skip('Unimplemented test')
def test_parser(self):
pass

def test_string_to_tokens(self):
self.assertEqual(
range_string.string_to_tokens("AA, 0.8(AKs)"),
[('AA', 1.0), ('AKs', 0.8)]
)

def test_validate_string(self):
true_cases = (
'ATs+, 80%(22-55)',
'ATs+,KQ, .2(4s9s)',
)
false_cases = (
'ATs+, KQ, .2(4s4s)',
'AX+',
)
for case in true_cases:
self.assertTrue(range_string.validate_string(case))
for case in false_cases:
self.assertFalse(range_string.validate_string(case))

def test_weight_to_float(self):
cases = (
(('86', '%'), 0.86),
(('3', ), 3),
(('0.7', ), 0.7),
(('.1', '%'), 0.001),
(('.1', ), 0.1),
)
for parsed_weight, value in cases:
self.assertAlmostEqual(
range_string.weight_to_float(parsed_weight), value, places=7
)

def test_expand_hand_type_group(self):
cases = (
(('ATs', '-', 'AQs'), ['ATs', 'AJs', 'AQs']),
(('JTn', '-', 'J8n'), ['J8o', 'J8s', 'J9o', 'J9s', 'JTo', 'JTs']),
(('55', '-', '99'), ['55', '66', '77', '88', '99']),
(('T7o', '+'), ['T7o', 'T8o', 'T9o']),
(('88', '+'), ['88', '99', 'TT', 'JJ', 'QQ', 'KK', 'AA']),
(('#', 'comment'), ['#comment']),
)

for htg, tokens in cases:
self.assertEqual(range_string.expand_hand_type_group(htg), tokens)

with self.assertRaises(range_string.RangeStringError):
range_string.expand_hand_type_group(('94o', '-', '97s'))
with self.assertRaises(range_string.RangeStringError):
range_string.expand_hand_type_group(('22', '-', '97s'))
with self.assertRaises(range_string.RangeStringError):
range_string.expand_hand_type_group(('J3s', '-', 'QQ'))

def test_token_to_hands(self):
cases = (
('ATs', [('Ac', 'Tc'), ('Ad', 'Td'), ('Ah', 'Th'), ('As', 'Ts')]),
('55', [('5s', '5h'), ('5s', '5d'), ('5s', '5c'), ('5h', '5d'),
('5h', '5c'), ('5d', '5c')]),
('74o', [('7s', '4h'), ('7s', '4d'), ('7s', '4c'), ('7h', '4s'),
('7h', '4d'), ('7h', '4c'), ('7d', '4s'), ('7d', '4h'),
('7d', '4c'), ('7c', '4s'), ('7c', '4h'), ('7c', '4d')]),
)

for token, hand_strings in cases:
self.assertEqual(
set(range_string.token_to_hands(token)), set(hand_strings)
)

def test_normalize_token(self):
cases = (
('ats', 'ATs'),
('25o', '52o'),
('7j', 'J7n'),
('qKs', 'KQs'),
('22', '22p'),
('As2d', 'As2d'),
('QsAc', 'AcQs'),
('2c2d', '2d2c'),
('#Comment', '#Comment'),
)

for token, normalized in cases:
self.assertEqual(range_string.normalize_token(token), normalized)

with self.assertRaises(range_string.RangeStringError):
range_string.normalize_token('77s')

def test_token_suitedness(self):
cases = (
('ATs', 's'),
('Q3o', 'o'),
('55', 'p'),
('J7', 'n'),
)

for token, suitedness in cases:
self.assertEqual(range_string.token_suitedness(token), suitedness)

with self.assertRaises(range_string.RangeStringError):
range_string.token_suitedness('22o')

suite = unittest.TestLoader().loadTestsFromTestCase(RangeStringTestCase)

0 comments on commit a74c859

Please sign in to comment.