update
This commit is contained in:
71
.planer/einheiten/backend__tft__sim__game.py.md
Normal file
71
.planer/einheiten/backend__tft__sim__game.py.md
Normal file
@@ -0,0 +1,71 @@
|
||||
# Einheiten: backend/tft/sim/game.py
|
||||
stand: f41ac76b5789
|
||||
|
||||
## backend/tft/sim/game.py::pair_players
|
||||
beschreibung: Ermittelt die PvP-Paarungen der lebenden Spieler und einen eventuellen Ghost-Gegner unter Vermeidung von Wiederholungsgegnern.
|
||||
input: Liste lebender PlayerState und ein random.Random
|
||||
output: Tupel aus Paaren, einem möglichen odd-Spieler und einem möglichen Ghost-Spieler
|
||||
entscheidungen:
|
||||
- Es werden bis zu 20 Shuffle-Versuche unternommen, um eine kollisionsfreie Paarung zu finden.
|
||||
beleg: "for _ in range(20):"
|
||||
- Wiederholungsgegner werden bei mehr als zwei Lebenden explizit ausgeschlossen.
|
||||
beleg: "all(a.last_opponent != b.name for a, b in pairs)"
|
||||
- Bei ungerader Spielerzahl wird ein Spieler als Ghost gegen einen zufälligen anderen gespiegelt.
|
||||
beleg: "ghost_src = rng.choice([p for p in alive if p is not odd]) if odd else None"
|
||||
- Die Paarungsinformation wird über last_opponent beidseitig festgehalten.
|
||||
beleg: "a.last_opponent, b.last_opponent = b.name, a.name"
|
||||
kanten:
|
||||
- nutzt: backend/tft/sim/player.py::PlayerState
|
||||
|
||||
## backend/tft/sim/game.py::Game
|
||||
beschreibung: Orchestriert eine komplette TFT-Partie als endliche Zustandsmaschine über Runden, Spielerauswahl und Kampfauswertung.
|
||||
input: artifact (dict), cfg (dict), optional seed (int)
|
||||
output: ein lauffähiger Spielzustand mit Spieler, Bots, Rundenplan, Pool und Log, der per `step()` voranschreitet
|
||||
entscheidungen:
|
||||
- Der Mensch steuert nur `self.player`, Bots werden fest auf 7 Instanzen aus rotierenden Archetypen aufgeteilt.
|
||||
beleg: "for i in range(7)"
|
||||
- Carousels laufen automatisch für alle ab, ohne Einkommen oder XP zu gewähren.
|
||||
beleg: "for p in self.players:"
|
||||
- Bei Rundenstart werden leere Shop-Slots vorbereitet, da zu 1-2 noch niemand Gold hat.
|
||||
beleg: "for p in self.players:"
|
||||
- Streak-Gold und Siegbonus werden ausschließlich in PvP-Runden gewertet, in PvE nicht.
|
||||
beleg: "if is_pvp:"
|
||||
- Augment-Angebote werden deterministisch pro Runde aus einer gewichteten Stufe gezogen, nicht pro Spieler separat.
|
||||
beleg: "self.rng.choices((1, 2, 3), weights=weights)[0]"
|
||||
kanten:
|
||||
- ruft-auf: backend/tft/sim/pool.py::Pool
|
||||
- ruft-auf: backend/tft/sim/player.py::new_player
|
||||
- ruft-auf: backend/tft/sim/player.py::score
|
||||
- ruft-auf: backend/tft/sim/player.py::grant_loot
|
||||
- ruft-auf: backend/tft/sim/player.py::grab_carousel_unit
|
||||
- ruft-auf: backend/tft/sim/player.py::buy
|
||||
- ruft-auf: backend/tft/sim/player.py::sell
|
||||
- ruft-auf: backend/tft/sim/player.py::reroll
|
||||
- ruft-auf: backend/tft/sim/player.py::buy_xp
|
||||
- ruft-auf: backend/tft/sim/player.py::move
|
||||
- ruft-auf: backend/tft/sim/player.py::equip
|
||||
- ruft-auf: backend/tft/sim/player.py::pick_augment
|
||||
- ruft-auf: backend/tft/sim/player.py::fill_board
|
||||
- ruft-auf: backend/tft/sim/player.py::merge
|
||||
- ruft-auf: backend/tft/sim/player.py::refresh_shop
|
||||
- ruft-auf: backend/tft/sim/policy.py::act
|
||||
- ruft-auf: backend/tft/sim/policy.py::ARCHETYPES
|
||||
- ruft-auf: backend/tft/sim/economy.py::apply_xp
|
||||
- ruft-auf: backend/tft/sim/economy.py::round_income
|
||||
- ruft-auf: backend/tft/sim/combat.py::fight
|
||||
- ruft-auf: backend/tft/sim/combat.py::player_damage
|
||||
- ruft-auf: backend/tft/sim/combat.py::pair_players
|
||||
- ruft-auf: backend/tft/sim/combat.py::board_profiles
|
||||
|
||||
## backend/tft/sim/game.py::_delegate
|
||||
beschreibung: Erzeugt eine Property, die Lese- und Schreibzugriff transparent an ein Attribut eines delegierten Objekts weiterreicht.
|
||||
input: ein Attributname als String
|
||||
output: ein `property`-Objekt mit Getter und Setter, die das gleichnamige Attribut auf `self.player` lesen bzw. schreiben
|
||||
entscheidungen:
|
||||
- Getter und Setter greifen beide über `self.player` auf das Zielattribut zu, sodass Aufrufer das Delegate-Objekt nicht vom echten Spieler unterscheiden müssen.
|
||||
beleg: "lambda self: getattr(self.player, attr)"
|
||||
- Schreibzugriff wird ebenfalls an `self.player` durchgereicht, wodurch das Delegate zweiseitig konsistent bleibt.
|
||||
beleg: "lambda self, value: setattr(self.player, attr, value)"
|
||||
- Die Attribute werden als ungeprüfte Strings übergeben, was eine sehr flexible, aber untypisierte Bindung an beliebige `player`-Attribute erlaubt.
|
||||
beleg: "attr: str"
|
||||
kanten:
|
||||
Reference in New Issue
Block a user