aboutsummaryrefslogtreecommitdiff
path: root/model.py
diff options
context:
space:
mode:
authorKaran Jayachandra <mail@karanjayachandra.com>2024-10-14 08:51:59 +0000
committerKaran Jayachandra <mail@karanjayachandra.com>2024-10-14 08:51:59 +0000
commiteac95cc2e259badf3a8c3309e6e7be97d5cbd868 (patch)
tree492b1497cf648e08e84a35dea2d217a57643dab0 /model.py
parent2b264abdf62822936e3510b0f9690ba1e359a9b8 (diff)
parentf80463a6437533deef1d85ffa31cf0cc5ed8e454 (diff)
Merge branch 'pure' into 'develop'
Dash to Flask HTML Conversion See merge request KaranJayachandra/match_up!1
Diffstat (limited to 'model.py')
-rw-r--r--model.py184
1 files changed, 184 insertions, 0 deletions
diff --git a/model.py b/model.py
new file mode 100644
index 0000000..a623d0a
--- /dev/null
+++ b/model.py
@@ -0,0 +1,184 @@
+from math import floor
+from csv import reader
+from pathlib import Path
+from random import sample
+from operator import attrgetter
+from dataclasses import dataclass
+
+
+@dataclass
+class Court:
+ number: int
+ status: bool
+
+
+@dataclass
+class CourtList:
+ total: int
+
+ def __post_init__(self):
+ self.courts = [Court(i + 1, True) for i in range(self.total)]
+ self.active = self.total
+
+ def get_court(self, court_number: int):
+ return [court for court in self.courts if court.number == court_number]
+
+ def toggle_court(self, court_number: int):
+ self.courts = [
+ (
+ Court(
+ number=court_number,
+ status=not court.status,
+ )
+ if court_number == court.number
+ else court
+ )
+ for court in self.courts
+ ]
+ self.active = sum([court.status for court in self.courts])
+
+
+@dataclass
+class Player:
+ name: str
+ skill: int = 0
+ status: bool = True
+
+
+class PlayerList:
+
+ def __init__(self, location: Path = "players.csv"):
+ players = []
+ with open(location, newline="") as file:
+ data_reader = reader(file)
+ next(data_reader, None)
+ for row in data_reader:
+ player = Player(name=row[0], skill=row[1], status=(row[2] == "True"))
+ players.append(player)
+ players.sort(key=attrgetter("name"))
+ self.players = players
+
+ def get_player(self, player_request: str):
+ players = [player for player in self.players if player.name == player_request]
+ players.sort(key=attrgetter("name"))
+ return players
+
+ def get_active_players(self):
+ players = [player for player in self.players if player.status]
+ players.sort(key=attrgetter("name"))
+ return players
+
+ def toggle_player(self, player_request: Player):
+ self.players = [
+ (
+ Player(
+ name=player.name,
+ skill=player.skill,
+ status=not player.status,
+ )
+ if player.name == player_request
+ else player
+ )
+ for player in self.players
+ ]
+
+ def __str__(self):
+ display_string = ""
+ for player in self.players:
+ display_string += player.__str__() + "\n"
+ return display_string
+
+
+@dataclass
+class Team:
+ player1: Player
+ player2: Player
+
+
+@dataclass
+class Game:
+ court: Court
+ team1: Team
+ team2: Team
+
+
+DUMMY_PLAYER = Player(name="-")
+DUMMY_TEAM = Team(player1=DUMMY_PLAYER, player2=DUMMY_PLAYER)
+
+
+def create_dummy_games(courts: list[Court]):
+ return [Game(court, DUMMY_TEAM, DUMMY_TEAM) for court in courts]
+
+
+RESERVED_PLAYER = Player(name="Reserved")
+RESERVED_TEAM = Team(player1=RESERVED_PLAYER, player2=RESERVED_PLAYER)
+
+
+def create_reserved_games(courts: list[Court]):
+ return [Game(court, RESERVED_TEAM, RESERVED_TEAM) for court in courts]
+
+
+PLAYER_PER_COURT = 4
+
+
+def create_single_game(court: Court, players: list[Player]):
+ team1 = Team(player1=players[0], player2=players[3])
+ team2 = Team(player1=players[1], player2=players[2])
+ return Game(court, team1, team2)
+
+
+def create_possible_games(court_list: list[Court], players: list[Player]):
+ clumped_players = [
+ players[i : i + PLAYER_PER_COURT]
+ for i in range(0, len(players), PLAYER_PER_COURT)
+ ]
+ games = [
+ create_single_game(court, clump)
+ for court, clump in zip(court_list, clumped_players)
+ ]
+ return games
+
+
+@dataclass
+class GameList:
+
+ def clear(self, court_list: CourtList):
+ courts = court_list.courts
+ active_courts = [court for court in courts if court.status]
+ inactive_courts = [court for court in courts if not court.status]
+ dummy_games = create_dummy_games(active_courts)
+ reserved_games = create_reserved_games(inactive_courts)
+ games = dummy_games + reserved_games
+ games.sort(key=attrgetter("court.number"))
+ self.games = games
+
+ def create_random_games(self, court_list: CourtList, player_list: PlayerList):
+ active_players = player_list.get_active_players()
+ active_courts = [court for court in court_list.courts if court.status]
+ inactive_courts = [court for court in court_list.courts if not court.status]
+ possible_games = floor(len(active_players) / PLAYER_PER_COURT)
+ current_players = sample(active_players, possible_games * PLAYER_PER_COURT)
+ active_games = create_possible_games(
+ active_courts[:possible_games], current_players
+ )
+ dummy_games = create_dummy_games(active_courts[possible_games:])
+ reserved_games = create_reserved_games(inactive_courts)
+ games = active_games + dummy_games + reserved_games
+ games.sort(key=attrgetter("court.number"))
+ self.games = games
+
+ def create_skilled_games(self, court_list: CourtList, player_list: PlayerList):
+ active_players = player_list.get_active_players()
+ active_courts = [court for court in court_list.courts if court.status]
+ inactive_courts = [court for court in court_list.courts if not court.status]
+ possible_games = floor(len(active_players) / PLAYER_PER_COURT)
+ current_players = sample(active_players, possible_games * PLAYER_PER_COURT)
+ current_players.sort(key=attrgetter("skill"))
+ active_games = create_possible_games(
+ active_courts[:possible_games], current_players
+ )
+ dummy_games = create_dummy_games(active_courts[possible_games:])
+ reserved_games = create_reserved_games(inactive_courts)
+ games = active_games + dummy_games + reserved_games
+ games.sort(key=attrgetter("court.number"))
+ self.games = games