import base import sys class GridManager: # orphans from earlier attempt offsetter = lambda x: x // 2 get_internal = lambda index: (index[0] + GridManager.offsetter(index[1]), index[1]) get_hex = lambda index: (index[0] - GridManager.offsetter(index[1]), index[1]) def __init__(self, size): self.grid = [ [0 for _ in range(size)] for _ in range(size) ] # orphan from earlier attempt self.board = base.Board(size) def internalize(self, stones: list) -> list: # orphan from earlier attempt return [list(map(self.get_internal, stone)) for stone in stones] def hexize(self, stones: list) -> list: # orphan from earlier attempt return [list(map(self.get_hex, stone)) for stone in stones] def place_stones(self, stones: list, placed: list, output_file: str) -> bool: if len(placed) == len(stones): return True curr = stones[len(placed)] color: int = stones.index(curr) + 1 for rotation in range(6): for p in range(-self.board.size, self.board.size): for q in range(-self.board.size, self.board.size): if self.board.inBoard(p, q) and self.check(curr, p, q): self.place_stone(curr, color, p, q) placed.append((p, q, rotation)) if self.place_stones(stones, placed, output_file): return True self.remove_stone(curr, p, q) placed.pop() curr = self.rotate_stone(curr) return False def rotate_stone(self, stone: list) -> list: rotated_stone = [(self.board.rotateLeft(x, y)) for (x, y) in stone] return rotated_stone def check(self, stone: list, *index: (int, int)) -> bool: for cell in stone: x, y = cell if ( not self.board.inBoard(index[0] + x, index[1] + y) or self.board.board[index[0] + x][index[1] + y] != 0 ): return False return True def place_stone(self, stone: list, color: int, *index: (int, int)) -> None: for cell in stone: x, y = cell self.board.board[index[0] + x][index[1] + y] = color def remove_stone(self, stone: list, *index: (int, int)) -> None: for cell in stone: x, y = cell self.board.board[index[0] + x][index[1] + y] = 0 def save_solution(self, output_file: str) -> None: with open(output_file, "w") as f: for p in self.board.board: for q in self.board.board[p]: f.write("{} {} {}\n".format(p, q, self.board.board[p][q])) if __name__ == "__main__": size: int = int(sys.argv[1]) gm: GridManager = GridManager(size) stones: list = base.loadStones(sys.argv[2]) output_file: str = sys.argv[3] placed_stones: list = [] tilesAmount: int = 0 totalSize: int = size**2 for stone in stones: tilesAmount += len(stone) if ( gm.place_stones(stones, placed_stones, output_file) == False or tilesAmount != totalSize ): with open(output_file, "w") as f: f.write("NOSOLUTION") else: # gm.board.saveImage("img.png") gm.save_solution(output_file)