From 0c4a446ec07b3b30541d75cb4e286258e5e5d0e8 Mon Sep 17 00:00:00 2001 From: Ivan Date: Sun, 19 Nov 2023 05:35:16 +0200 Subject: [PATCH 1/2] Solution --- app/main.py | 113 ++++++++++++++++++++++++++++++++++++++++------------ 1 file changed, 88 insertions(+), 25 deletions(-) diff --git a/app/main.py b/app/main.py index 626f41cf..5191ef5d 100644 --- a/app/main.py +++ b/app/main.py @@ -1,34 +1,97 @@ class Deck: - def __init__(self, row, column, is_alive=True): - pass + def __init__( + self, + row: int, + column: int, + is_alive: bool = True + ) -> None: + self.row = row + self.column = column + self.is_alive = is_alive class Ship: - def __init__(self, start, end, is_drowned=False): - # Create decks and save them to a list `self.decks` - pass + def __init__( + self, + start: int, + end: int, + is_drowned: bool = False + ) -> None: + self.decks = [Deck(row, col) + for row, col in self.get_coordinates(start, end)] + self.is_drowned = is_drowned - def get_deck(self, row, column): - # Find the corresponding deck in the list - pass + @classmethod + def get_coordinates( + cls, + start: tuple, + end: tuple + ) -> list[tuple]: + return [(start[0] + i, start[1] + j) + for i in range(end[0] - start[0] + 1) + for j in range(end[1] - start[1] + 1)] - def fire(self, row, column): - # Change the `is_alive` status of the deck - # And update the `is_drowned` value if it's needed - pass + def get_deck( + self, + row: int, + column: int + ) -> Deck | None: + return next((deck for deck in self.decks if deck.row + == row and deck.column == column), None) + + def fire( + self, + row: int, + column: int + ) -> None: + deck = self.get_deck(row, column) + if deck: + deck.is_alive = False + if all(not deck_.is_alive for deck_ in self.decks): + self.is_drowned = True class Battleship: - def __init__(self, ships): - # Create a dict `self.field`. - # Its keys are tuples - the coordinates of the non-empty cells, - # A value for each cell is a reference to the ship - # which is located in it - pass - - def fire(self, location: tuple): - # This function should check whether the location - # is a key in the `self.field` - # If it is, then it should check if this cell is the last alive - # in the ship or not. - pass + def __init__( + self, + ships: list + ) -> None: + self.field = {} + for ship_start, ship_end in ships: + ship = Ship(ship_start, ship_end) + for deck in ship.decks: + self.field[(deck.row, deck.column)] = ship + + def fire( + self, + location: tuple + ) -> str: + if location not in self.field: + return "Miss!" + + ship = self.field[location] + deck = ship.get_deck(*location) + + if deck.is_alive: + ship.fire(location[0], location[1]) + if ship.is_drowned: + return "Sunk!" + return "Hit!" + return "Miss!" + + def print_field(self) -> None: + for row in range(10): + for col in range(10): + location = (row, col) + if location in self.field: + ship = self.field[location] + deck = ship.get_deck(row, col) + if deck.is_alive: + print(u"\u25A1", end=" ") + elif ship.is_drowned: + print("x", end=" ") + else: + print("*", end=" ") + else: + print("~", end=" ") + print() From 80d8026a33bb006739001c22fe9ef9c7c52c59f4 Mon Sep 17 00:00:00 2001 From: Ivan Date: Mon, 20 Nov 2023 05:47:08 +0200 Subject: [PATCH 2/2] Fixed solution --- app/main.py | 39 ++++++++++----------------------------- 1 file changed, 10 insertions(+), 29 deletions(-) diff --git a/app/main.py b/app/main.py index 5191ef5d..1372a99b 100644 --- a/app/main.py +++ b/app/main.py @@ -21,29 +21,17 @@ def __init__( for row, col in self.get_coordinates(start, end)] self.is_drowned = is_drowned - @classmethod - def get_coordinates( - cls, - start: tuple, - end: tuple - ) -> list[tuple]: + @staticmethod + def get_coordinates(start: tuple, end: tuple) -> list[tuple]: return [(start[0] + i, start[1] + j) for i in range(end[0] - start[0] + 1) for j in range(end[1] - start[1] + 1)] - def get_deck( - self, - row: int, - column: int - ) -> Deck | None: + def get_deck(self, row: int, column: int) -> Deck | None: return next((deck for deck in self.decks if deck.row == row and deck.column == column), None) - def fire( - self, - row: int, - column: int - ) -> None: + def fire(self, row: int, column: int) -> None: deck = self.get_deck(row, column) if deck: deck.is_alive = False @@ -52,20 +40,13 @@ def fire( class Battleship: - def __init__( - self, - ships: list - ) -> None: - self.field = {} - for ship_start, ship_end in ships: - ship = Ship(ship_start, ship_end) - for deck in ship.decks: - self.field[(deck.row, deck.column)] = ship + def __init__(self, ships: list) -> None: + self.field = {(deck.row, deck.column): ship + for ship_start, ship_end in ships + for ship in [Ship(ship_start, ship_end)] + for deck in ship.decks} - def fire( - self, - location: tuple - ) -> str: + def fire(self, location: tuple) -> str: if location not in self.field: return "Miss!"