-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathshoe.py
More file actions
65 lines (56 loc) · 2.12 KB
/
Copy pathshoe.py
File metadata and controls
65 lines (56 loc) · 2.12 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
import random
from typing import List
class BlackjackShoe:
def __init__(self, num_decks: int = 6):
"""
Args:
num_decks: Number of standard 52-card decks.
"""
self.num_decks = num_decks
self.cards: List[int] = []
self.dealt_cards: List[int] = []
self.running_count = 0
self.reset_shoe()
def reset_shoe(self) -> None:
"""Creates a fresh shoe, shuffles, and randomizes penetration."""
# Standard deck: 2-9 (8 cards), four 10s (10, J, Q, K), and Ace (11)
one_deck = [2, 3, 4, 5, 6, 7, 8, 9, 10, 10, 10, 10, 11] * 4
self.cards = one_deck * self.num_decks
random.shuffle(self.cards)
# Reset tracking variables
self.dealt_cards = []
self.running_count = 0
# Randomize penetration between 0.60 and 0.85 (common casino range)
self.penetration = random.uniform(0.60, 0.85)
self.cut_card_index = int(len(self.cards) * (1 - self.penetration))
def draw(self) -> int:
"""Draws a card and updates the Hi-Lo running count."""
if len(self.cards) <= self.cut_card_index:
self.reset_shoe()
card = self.cards.pop()
self.dealt_cards.append(card)
self.update_running_count(card)
return card
def update_running_count(self, card: int) -> None:
"""
Hi-Lo Counting Logic:
2-6: +1
7-9: 0
10, J, Q, K, A: -1
"""
if 2 <= card <= 6:
self.running_count += 1
elif card >= 10: # Includes 10, J, Q, K (10) and Ace (11)
self.running_count -= 1
def get_count(self) -> float:
"""
Returns the 'True Count'.
True Count = Running Count / Decks Remaining.
This is more useful for RL agents than the running count.
"""
decks_remaining = len(self.cards) / 52
if decks_remaining < 0.1: # Prevent division by zero
return float(self.running_count)
return round(self.running_count / decks_remaining, 2)
def cards_remaining(self) -> int:
return len(self.cards)