Skip to content

Instantly share code, notes, and snippets.

@jmanian
Last active June 3, 2016 18:20
Show Gist options
  • Save jmanian/c1aa5b96936f81c5d482ce84b2a8a994 to your computer and use it in GitHub Desktop.
Save jmanian/c1aa5b96936f81c5d482ce84b2a8a994 to your computer and use it in GitHub Desktop.
# matchup format:
# favorite, underdog, p fave wins at home, p fave wins away, series score so far
matchups = [
# ['GSW', 'HOU', 0.87, 0.69, [0, 0]],
# ['SAS', 'MEM', 0.92, 0.78, [0, 0]],
# ['OKC', 'DAL', 0.82, 0.59, [0, 0]],
# ['LAC', 'POR', 0.71, 0.45, [0, 0]],
# ['CLE', 'DET', 0.80, 0.56, [0, 0]],
# ['TOR', 'IND', 0.79, 0.55, [0, 0]],
# ['MIA', 'CHA', 0.62, 0.35, [0, 0]],
# ['ATL', 'BOS', 0.67, 0.40, [0, 0]],
['GSW', 'CLE', 0.72, 0.47, [1, 0]]
]
scores = [
[10, 6, 4, 3, 0, 0, 0, 0],
[6, 8, 6, 4, 1, 0, 0, 0],
[4, 6, 8, 6, 2, 1, 0, 0],
[3, 4, 6, 8, 4, 2, 1, 0],
[0, 1, 2, 4, 8, 6, 4, 3],
[0, 0, 1, 2, 6, 8, 6, 4],
[0, 0, 0, 1, 4, 6, 8, 6],
[0, 0, 0, 0, 3, 4, 6, 10]
]
outcome_labels = ['4-0', '4-1', '4-2', '4-3', '3-4', '2-4', '1-4', '0-4']
# is the next game a home game?
def is_home(wins, losses):
return wins + losses + 1 in [1, 2, 5, 7]
# returns the index for the outcome
def index(wins, losses):
if wins == 4:
return losses
elif losses == 4:
return 7 - wins
# recursively walk through the tree of possibilities
# calculate the probability of each path
# and add up the probabilities for each outcome
# wins: favorite's wins at this point in the tree
# losses: favorite's losses at this point in the tree
# p: probability of reaching this node in the tree, using the exact path taken
# p_win_home: probability that favorite wins at home
# p_win_away: probability that favorite wins away
def play_games(wins, losses, p, p_win_home, p_win_away):
# check whether the series is already over
# if so then return the probability array with `p` for the result and the rest as 0
if 4 in [wins, losses]:
a = [0] * 8
a[index(wins, losses)] = p
return a
# assign the probabilities, based on who is the home team
p_win = p_win_home if is_home(wins, losses) else p_win_away
p_lose = 1 - p_win
# get the probabilitiy array given that the favored team wins this game
win_results = play_games(wins + 1, losses, p*p_win, p_win_home, p_win_away)
# get the probability array given that the underdog wins this game
lose_results = play_games(wins, losses + 1, p*p_lose, p_win_home, p_win_away)
# add the two arrays together
return map(sum, zip(win_results, lose_results)) # vector addition
for [team1, team2, p_win_home, p_win_away, results] in matchups:
# compute probabilities of all 8 results, print the max
probabilities = play_games(results[0], results[1], 1, p_win_home, p_win_away)
print "mode: %s %s %s" % (team1, outcome_labels[probabilities.index(max(probabilities))], team2)
# compute the expected score for picking each result, print the max
expected_scores = [sum(p*s for p, s in zip(probabilities, guess)) for guess in scores]
print "max EV: %s %s %s" % (team1, outcome_labels[expected_scores.index(max(expected_scores))], team2)
# print all probabilities and all expected scores
probabilities = [round(p*100, 2) for p in probabilities]
expected_scores = [round(e, 2) for e in expected_scores]
print "probabilities: %s" % probabilities
print "expected scores: %s" % expected_scores
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment