class GoGame:
    def __init__(self, size=9):
        self.size = size
        self.board = [[None for _ in range(size)] for _ in range(size)]
        self.current_player = 'B'
        self.pass_count = 0
        self.captured = {'B': 0, 'W': 0}
        self.ko_point = None

    def print_board(self):
        print("  A B C D E F G H J")
        for i in range(self.size):
            row = f"{i+1} "
            for j in range(self.size):
                stone = self.board[i][j]
                if stone is None:
                    row += ". "
                else:
                    row += f"{stone} "
            print(row)
        print()

    def is_valid_move(self, row, col):
        if not (0 <= row < self.size and 0 <= col < self.size):
            return False
        if self.board[row][col] is not None:
            return False
        return True

    def get_neighbors(self, row, col):
        neighbors = []
        for dr, dc in [(-1, 0), (1, 0), (0, -1), (0, 1)]:
            r, c = row + dr, col + dc
            if 0 <= r < self.size and 0 <= c < self.size:
                neighbors.append((r, c))
        return neighbors

    def get_group(self, row, col, visited=None):
        if visited is None:
            visited = set()
        if (row, col) in visited:
            return set(), 0
        visited.add((row, col))
        stone = self.board[row][col]
        if stone is None:
            return set(), 1
        group = {(row, col)}
        liberties = 0
        for r, c in self.get_neighbors(row, col):
            if (r, c) not in visited:
                if self.board[r][c] == stone:
                    sub_group, sub_liberties = self.get_group(r, c, visited)
                    group.update(sub_group)
                    liberties += sub_liberties
                elif self.board[r][c] is None:
                    liberties += 1
        return group, liberties

    def capture_group(self, group):
        for row, col in group:
            self.board[row][col] = None

    def would_be_suicide(self, row, col, player):
        # Temporarily place the stone
        self.board[row][col] = player
        # Check if any opponent group has no liberties
        opponent = 'W' if player == 'B' else 'B'
        captured_groups = []
        for r, c in self.get_neighbors(row, col):
            if self.board[r][c] == opponent:
                group, liberties = self.get_group(r, c)
                if liberties == 0:
                    captured_groups.append(group)
        # If we capture something, it's not suicide
        if captured_groups:
            # Revert the temporary placement
            self.board[row][col] = None
            return False
        # Check if our own group has liberties
        group, liberties = self.get_group(row, col)
        # Revert the temporary placement
        self.board[row][col] = None
        return liberties == 0

    def play_move(self, row, col):
        if not self.is_valid_move(row, col):
            return False
        if self.would_be_suicide(row, col, self.current_player):
            return False
        # Check for ko (simple version)
        if (row, col) == self.ko_point:
            return False
            
        # Place the stone
        self.board[row][col] = self.current_player
        
        # Capture opponent groups
        opponent = 'W' if self.current_player == 'B' else 'B'
        captured_count = 0
        for r, c in self.get_neighbors(row, col):
            if self.board[r][c] == opponent:
                group, liberties = self.get_group(r, c)
                if liberties == 0:
                    self.capture_group(group)
                    captured_count += len(group)
        
        self.captured[opponent] += captured_count
        
        # Update ko point if exactly one stone was captured
        if captured_count == 1:
            # Find the captured stone position
            for r, c in self.get_neighbors(row, col):
                if self.board[r][c] is None:
                    # Check if it was the only stone in its group
                    # This is a simplification - real ko is more complex
                    self.ko_point = (r, c)
                    break
        else:
            self.ko_point = None
            
        return True

    def pass_turn(self):
        self.pass_count += 1
        return True

    def switch_player(self):
        self.current_player = 'W' if self.current_player == 'B' else 'B'

    def score_game(self):
        # Simple scoring: stones captured
        return self.captured['B'], self.captured['W']

    def play(self):
        while self.pass_count < 2:
            self.print_board()
            player_name = "Black" if self.current_player == 'B' else "White"
            move = input(f"{player_name} to play (e.g., E5) or 'pass': ").strip().upper()
            
            if move == 'PASS':
                self.pass_turn()
                self.switch_player()
                continue
            
            if len(move) < 2:
                print("Invalid move. Please use format like 'E5' or 'pass'.")
                continue
                
            col_char = move[0]
            if col_char not in 'ABCDEFGHJ':  # Skip I
                print("Invalid column. Use A-J (skipping I).")
                continue
                
            col = 'ABCDEFGHJ'.index(col_char)
            
            try:
                row = int(move[1:]) - 1
            except ValueError:
                print("Invalid row. Use a number from 1-9.")
                continue
                
            if not (0 <= row < self.size):
                print("Row out of bounds. Use 1-9.")
                continue
                
            if self.play_move(row, col):
                self.pass_count = 0  # Reset pass count after a move
                self.switch_player()
            else:
                print("Invalid move. Try again.")
        
        self.print_board()
        b_score, w_score = self.score_game()
        print(f"Game over!")
        print(f"Black captured: {b_score}")
        print(f"White captured: {w_score}")
        if b_score > w_score:
            print("Black wins!")
        elif w_score > b_score:
            print("White wins!")
        else:
            print("Tie!")

if __name__ == "__main__":
    game = GoGame()
    game.play()
