reorder function definitions so dataclasses come first

This commit is contained in:
Michael Pilosov 2022-11-26 22:38:46 -07:00
parent 0ecb6ef192
commit 6c16d2986b
2 changed files with 138 additions and 138 deletions

View File

@ -120,143 +120,6 @@ ALIASES = {
CHIP_VALUES = {0.25, 0.5, 1, 5, 10, 25, 50, 100}
def expected(bet: Bet) -> float:
"""
Returns the expected value of a bet.
Parameters
----------
bet : Bet
The bet to calculate the expected value of.
Returns
-------
float
The expected value of the bet.
"""
bets = list(bet.spread.values())
cond_bets = filter(lambda x: x > 0, bets)
amt = sum(bets)
payout = amt * 36 / 38
print(
f"bet: {amt:.2f}, expected: {payout:.2f}: {payout/amt:2.4f}"
+ f"with std {stdev(bets*36)} mean win of"
+ f"{36*mean(cond_bets)} {sum(filter(lambda x: x > 0, bets))}/38 times."
)
return payout
def place_bet(bet: Bet, on: int, amount: float) -> Bet:
"""
Places a bet on a number.
Parameters
----------
bet : Bet
The bet to place.
on : int
The number to bet on.
amount : float
The amount to bet.
Returns
-------
Bet
A dictionary representing the bet with the new bet placed.
"""
bet = bet.copy()
bet[on] += amount
return bet
def interpret_bet(on="red", amount=0, bet=Optional[Bet]) -> Bet:
"""
Interprets a bet and returns a dictionary representing the bet.
Parameters
----------
on : str
The type of bet to place.
amount : float
The amount to bet.
bet : Bet
The bet to add to.
(default is None, which creates a new bet)
Returns
-------
Bet
A dictionary representing the bet.
"""
assert (on in FEASIBLE_MOVES) or (
on in ALIASES
), f"Bet `{on}` not understood. Choose from feasible moves:\n {FEASIBLE_MOVES}"
if bet is None:
bet = Bet()
else:
bet = bet.copy()
REDS = {1, 3, 5, 7, 9, 12, 14, 16, 18, 19, 21, 23, 25, 27, 30, 32, 34, 36}
BLACKS = set(range(37)) - REDS
NUMS = {}
on = on.strip().replace(" ", "-")
div = 18
if on in ("red", "reds"):
NUMS = REDS
if on in ("black", "blacks"):
NUMS = BLACKS
if on in ("odd", "odds"):
NUMS = {i for i in range(1, 37) if i % 2 == 0}
if on in ("even", "evens"):
NUMS = {i for i in range(1, 37) if i % 2}
if on in ("1-18", "first-18", "first-half"):
NUMS = set(range(1, 19))
if on in ("19-36", "last-18", "last-half", "second-half", "second-18"):
NUMS = set(range(19, 37))
if on in ("1-12", "13-24", "25-36"):
low, high = on.split("-")
NUMS = set(range(int(low), int(high) + 1))
div = 12
if on in ["triple-0", "triple-00"]:
NUMS = {0, 1, 2} if on == "triple-0" else {-1, 2, 3}
div = 3
if not NUMS:
other_bet = on.split("-")
if other_bet[0] == "street":
street = int(other_bet[1]) - 1
assert street in list(range(13))
NUMS = {i for i in range(street + 1, street + 4)}
div = 3
elif other_bet[0] == "col":
col = int(other_bet[1]) - 1
assert col in list(range(0, 3))
NUMS = {i for i in range(1, 37) if (i - 1) % 3 == col}
div = 12
elif (
other_bet[0] == "split"
): # TODO: validate choices, for now we disallow these.
num_1, num_2 = int(other_bet[1]), int(other_bet[2])
NUMS = {num_1, num_2}
div = 2
elif other_bet[0] == "corner":
num_1, num_2 = int(other_bet[1]), int(other_bet[2])
num_3, num_4 = int(other_bet[3]), int(other_bet[4])
NUMS = {num_1, num_2, num_3, num_4}
div = 4
else:
try:
NUMS = {int(on)}
div = 1
except ValueError as e:
raise e(
f"Bet `{on}` not understood."
+ f"Choose from feasible moves:\n {set(range(-1, 37))}"
)
bet = reduce(lambda bet, num: place_bet(bet, num, amount / div), NUMS, bet)
return bet
@dataclass
class Placement:
"""
@ -454,6 +317,143 @@ class Player:
return self.id < other.id
def expected(bet: Bet) -> float:
"""
Returns the expected value of a bet.
Parameters
----------
bet : Bet
The bet to calculate the expected value of.
Returns
-------
float
The expected value of the bet.
"""
bets = list(bet.spread.values())
cond_bets = filter(lambda x: x > 0, bets)
amt = sum(bets)
payout = amt * 36 / 38
print(
f"bet: {amt:.2f}, expected: {payout:.2f}: {payout/amt:2.4f}"
+ f"with std {stdev(bets*36)} mean win of"
+ f"{36*mean(cond_bets)} {sum(filter(lambda x: x > 0, bets))}/38 times."
)
return payout
def place_bet(bet: Bet, on: int, amount: float) -> Bet:
"""
Places a bet on a number.
Parameters
----------
bet : Bet
The bet to place.
on : int
The number to bet on.
amount : float
The amount to bet.
Returns
-------
Bet
A dictionary representing the bet with the new bet placed.
"""
bet = bet.copy()
bet[on] += amount
return bet
def interpret_bet(on="red", amount=0, bet=Optional[Bet]) -> Bet:
"""
Interprets a bet and returns a dictionary representing the bet.
Parameters
----------
on : str
The type of bet to place.
amount : float
The amount to bet.
bet : Bet
The bet to add to.
(default is None, which creates a new bet)
Returns
-------
Bet
A dictionary representing the bet.
"""
assert (on in FEASIBLE_MOVES) or (
on in ALIASES
), f"Bet `{on}` not understood. Choose from feasible moves:\n {FEASIBLE_MOVES}"
if bet is None:
bet = Bet()
else:
bet = bet.copy()
REDS = {1, 3, 5, 7, 9, 12, 14, 16, 18, 19, 21, 23, 25, 27, 30, 32, 34, 36}
BLACKS = set(range(37)) - REDS
NUMS = {}
on = on.strip().replace(" ", "-")
div = 18
if on in ("red", "reds"):
NUMS = REDS
if on in ("black", "blacks"):
NUMS = BLACKS
if on in ("odd", "odds"):
NUMS = {i for i in range(1, 37) if i % 2 == 0}
if on in ("even", "evens"):
NUMS = {i for i in range(1, 37) if i % 2}
if on in ("1-18", "first-18", "first-half"):
NUMS = set(range(1, 19))
if on in ("19-36", "last-18", "last-half", "second-half", "second-18"):
NUMS = set(range(19, 37))
if on in ("1-12", "13-24", "25-36"):
low, high = on.split("-")
NUMS = set(range(int(low), int(high) + 1))
div = 12
if on in ["triple-0", "triple-00"]:
NUMS = {0, 1, 2} if on == "triple-0" else {-1, 2, 3}
div = 3
if not NUMS:
other_bet = on.split("-")
if other_bet[0] == "street":
street = int(other_bet[1]) - 1
assert street in list(range(13))
NUMS = {i for i in range(street + 1, street + 4)}
div = 3
elif other_bet[0] == "col":
col = int(other_bet[1]) - 1
assert col in list(range(0, 3))
NUMS = {i for i in range(1, 37) if (i - 1) % 3 == col}
div = 12
elif (
other_bet[0] == "split"
): # TODO: validate choices, for now we disallow these.
num_1, num_2 = int(other_bet[1]), int(other_bet[2])
NUMS = {num_1, num_2}
div = 2
elif other_bet[0] == "corner":
num_1, num_2 = int(other_bet[1]), int(other_bet[2])
num_3, num_4 = int(other_bet[3]), int(other_bet[4])
NUMS = {num_1, num_2, num_3, num_4}
div = 4
else:
try:
NUMS = {int(on)}
div = 1
except ValueError as e:
raise e(
f"Bet `{on}` not understood."
+ f"Choose from feasible moves:\n {set(range(-1, 37))}"
)
bet = reduce(lambda bet, num: place_bet(bet, num, amount / div), NUMS, bet)
return bet
def simulate_random_strategy(min_num_games=1, total_budget=200) -> Strategy:
"""
Simulates a random strategy based on the minimum number of games that

View File

@ -10,7 +10,7 @@ with open(BASEDIR.joinpath("README.md"), "r") as fp:
setup(
name="pyroulette",
version="0.0.1rc4",
version="0.0.1rc5",
description="A package for exploring roulette strategies.",
long_description=LONG_DESCRIPTION,
long_description_content_type="text/markdown",