Ich habe eine 2500-Linien- Character
Klasse, die:
- Verfolgt den internen Status des Charakters im Spiel.
- Lädt diesen Zustand und behält ihn bei.
- Verarbeitet ~ 30 eingehende Befehle (normalerweise = leitet sie an weiter
Game
, aber einige schreibgeschützte Befehle werden sofort beantwortet). - Erhält ca. 80 Anrufe
Game
bezüglich der durchgeführten Aktionen und der relevanten Aktionen anderer.
Es scheint mir, dass Character
es eine einzige Aufgabe ist: den Zustand des Charakters zu verwalten und zwischen eingehenden Befehlen und dem Spiel zu vermitteln.
Es gibt noch einige andere Verantwortlichkeiten, die bereits aufgeschlüsselt wurden:
Character
hat eine, inOutgoing
die es ruft, um ausgehende Updates für die Client-Anwendung zu generieren.Character
hat eineTimer
welche spuren wann es das nächste mal erlaubt ist etwas zu machen. Eingehende Befehle werden dagegen validiert.
Meine Frage ist also, ist es akzeptabel, eine so große Klasse unter SRP und ähnlichen Prinzipien zu haben? Gibt es bewährte Methoden, um die Arbeit zu erleichtern (z. B. das Aufteilen von Methoden in separate Dateien)? Oder fehlt mir etwas und gibt es wirklich eine gute Möglichkeit, es aufzuteilen? Mir ist klar, dass dies sehr subjektiv ist und ich möchte Feedback von anderen.
Hier ist ein Beispiel:
class Character(object):
def __init__(self):
self.game = None
self.health = 1000
self.successful_attacks = 0
self.points = 0
self.timer = Timer()
self.outgoing = Outgoing(self)
def load(self, db, id):
self.health, self.successful_attacks, self.points = db.load_character_data(id)
def save(self, db, id):
db.save_character_data(self, health, self.successful_attacks, self.points)
def handle_connect_to_game(self, game):
self.game.connect(self)
self.game = game
self.outgoing.send_connect_to_game(game)
def handle_attack(self, victim, attack_type):
if time.time() < self.timer.get_next_move_time():
raise Exception()
self.game.request_attack(self, victim, attack_type)
def on_attack(victim, attack_type, points):
self.points += points
self.successful_attacks += 1
self.outgoing.send_attack(self, victim, attack_type)
self.timer.add_attack(attacker=True)
def on_miss_attack(victim, attack_type):
self.missed_attacks += 1
self.outgoing.send_missed_attack()
self.timer.add_missed_attack()
def on_attacked(attacker, attack_type, damage):
self.start_defenses()
self.take_damage(damage)
self.outgoing.send_attack(attacker, self, attack_type)
self.timer.add_attack(victim=True)
def on_see_attack(attacker, victim, attack_type):
self.outgoing.send_attack(attacker, victim, attack_type)
self.timer.add_attack()
class Outgoing(object):
def __init__(self, character):
self.character = character
self.queue = []
def send_connect_to_game(game):
self._queue.append(...)
def send_attack(self, attacker, victim, attack_type):
self._queue.append(...)
class Timer(object):
def get_next_move_time(self):
return self._next_move_time
def add_attack(attacker=False, victim=False):
if attacker:
self.submit_move()
self.add_time(ATTACK_TIME)
if victim:
self.add_time(ATTACK_VICTIM_TIME)
class Game(object):
def connect(self, character):
if not self._accept_character(character):
raise Exception()
self.character_manager.add(character)
def request_attack(character, victim, attack_type):
if victim.has_immunity(attack_type):
character.on_miss_attack(victim, attack_type)
else:
points = self._calculate_points(character, victim, attack_type)
damage = self._calculate_damage(character, victim, attack_type)
character.on_attack(victim, attack_type, points)
victim.on_attacked(character, attack_type, damage)
for other in self.character_manager.get_observers(victim):
other.on_see_attack(character, victim, attack_type)
db.save_character_data(self, health, self.successful_attacks, self.points)
Du hastself.health
richtig gemeint ?