Files
tft/.planer/einheiten/backend__tft__sim__game.py.md
2026-07-24 11:24:24 +02:00

4.0 KiB

Einheiten: backend/tft/sim/game.py

stand: f41ac76b57

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: