def __init__(self, ptype, mm): self.ptype = ptype if ptype > 0: print("create player minimax/alphabeta") self.tree = GameTree(mm) else: print("create player human")
def run_ai_mode(): """ Run Connect 3 against AI on a 3x3 board """ player = player_piece() rows = 3 cols = 3 game = Connect3Board(rows, cols) print(game) game_tree = GameTree(game) position = game_tree.get_root_position() while game.get_winner() is None: if game.get_whose_turn() == player: move = get_int( "Your turn. Choose column (0 to {}): ".format(cols - 1), 0, cols - 1) if game.can_add_token_to_column(move) is True: game.add_token(move) position = position.get_child(move) print(game) else: print("ERROR: Invalid move, please try again") else: children_scores = position.get_children_scores() child_index = None max_score = -2 min_score = 2 for i, child in enumerate(children_scores): if game.get_whose_turn() == game.TOKENS[0]: if child is not None and child > max_score: max_score = child child_index = i else: if child is not None and child < min_score: min_score = child child_index = i game.add_token(child_index) position = position.get_child(child_index) print("AI's turn") print(game) if game.get_winner() == Connect3Board.DRAW: print("This game has ended in a draw!") else: print("Player {} wins!".format(game.get_winner()))
class Player: nextmove = None gametree = None ptype = 0 tree = None game = None i = 0 def __init__(self, ptype, mm): self.ptype = ptype if ptype > 0: print("create player minimax/alphabeta") self.tree = GameTree(mm) else: print("create player human") def setGame(self, game): self.game = game if self.ptype > 0: self.tree.createTree(game) @threaded def nextMove(self): print("calc next move") realmove = -1 count = 0 while realmove == -1 and count < self.game.fields: if 0 > self.i: print("to small move number") self.i = 0 elif self.i >= (self.game.allfields / 2) - 1: print("to big move number") self.i = 0 else: count += 1 if self.game.allbeans[self.i] > 0: realmove = self.i print("found move: " + str(realmove)) else: print("no beans next") self.i += 1 count += 1 time.sleep(5) self.game.do_move(self, realmove)
def main(m, n, k, depth_lim): game = MNKgame(m=m, n=n, k=k) gametree = GameTree(game) minimax_algorithm = Minimax_algorithm(game, gametree, depth_lim=depth_lim) me = Player(game, gametree, 1) enemy = Enemy(game, -1, policy=minimax_algorithm) turn = 0 is_player_first = True while turn < game.n * game.m: if is_player_first: me.play() if game.winner != 0: break enemy.play() else: enemy.play() if game.winner != 0: break me.play() if game.winner != 0: break turn += 2 if game.winner == 0: print("DRAW GAME")
def test_minmax_algorithm_play_optimal_game(): field = [[1, -1, 0], [0, 1, 0], [0, -1, 0]] game = MNKgame(field=np.array(field)) gametree = GameTree(game) minimax_algo = Minimax_algorithm(game, gametree) enemy = Enemy(game, -1, policy=minimax_algo) enemy2 = Enemy(game, 1, policy=minimax_algo) enemy.play() field_out = [[1, -1, 0], [0, 1, 0], [0, -1, -1]] assert np.array_equal(game.field, field_out) enemy2.play() field_out = [[1, -1, 0], [0, 1, 0], [1, -1, -1]] assert np.array_equal(game.field, field_out) enemy.play() field_out = [[1, -1, -1], [0, 1, 0], [1, -1, -1]] assert np.array_equal(game.field, field_out) enemy2.play() field_out = [[1, -1, -1], [1, 1, 0], [1, -1, -1]] assert np.array_equal(game.field, field_out)
def run_ai_mode(): board = Connect3Board(3, 3) player_token = select_player_token() game_tree = GameTree(board) print(game_tree.count) position_tree = game_tree.get_root_position() while board.get_winner() == None: if board.get_whose_turn() == player_token: print(board) column_choice = get_int( "Player {}'s turn. Choose column ({} to {}):".format( board.get_whose_turn(), 0, board.get_columns() - 1)) if board.can_add_token_to_column(column_choice): board.add_token(column_choice) # find the children from the tree based on the users selection position_tree = position_tree.get_child(column_choice) else: print("You cannot add a token at column {}".format( column_choice)) else: print("AI's turn") child_scores = position_tree.get_children_scores() # select the best child score from the children best_child = 0 for index, score in enumerate(child_scores): # pick the score based on player selecting O token if score is not None and player_token != GameTree.MIN_PLAYER and score < GameTree.MAX_WIN_SCORE: best_child = index # pick the best score based on player selecting # token elif score is not None and player_token != GameTree.MAX_PLAYER and score > GameTree.MIN_WIN_SCORE: best_child = index board.add_token(best_child) # navigate to the next child in the tree position_tree = position_tree.get_child(best_child) print(board) # Display the winner if its not a draw if board.get_winner() != board.DRAW: print("Player {} wins!".format(board.get_winner())) else: print(board.get_winner())
def test_enemy_cannot_place(): field = [[-1, 1, -1], [1, -1, 1], [-1, 1, -1]] game = MNKgame(field=np.array(field)) gametree = GameTree(game) minimax_algo = Minimax_algorithm(game, gametree) enemy = Enemy(game, -1, policy=minimax_algo) enemy.play()
def test_game_will_finish(): field = [[1, -1, -1], [1, 1, 0], [-1, -1, 0]] game = MNKgame(field=np.array(field)) gametree = GameTree(game) minimax_algo = Minimax_algorithm(game, gametree) enemy = Enemy(game, -1, policy=minimax_algo) enemy.play() assert game.winner == -1
def main(): test = Connect3Board(3, 3) Tree = GameTree(test) print('Welcome to Connect 3 by Kevin Richards') mode = get_mode() while mode != 'Q': if mode == 'A': run_two_player_mode() elif mode == 'B': run_ai_mode(Tree) mode = get_mode()
def test_player_place_piece(mocker): field = [[0, 0, 0], [0, 0, 0], [0, 0, 0]] game = MNKgame(field=np.array(field)) gametree = GameTree(game) player = Player(game, gametree, 1) mocker.patch("player.Player.receive_input", return_value=(0, 0)) player.play() field_out = [[1, 0, 0], [0, 0, 0], [0, 0, 0]] assert np.array_equal(game.field, field_out)
def test_minmax_algorithm_chose_win(): field = [[1, -1, -1], [1, 1, 0], [-1, -1, 0]] game = MNKgame(field=np.array(field)) gametree = GameTree(game) minimax_algo = Minimax_algorithm(game, gametree) enemy = Enemy(game, -1, policy=minimax_algo) enemy.play() print(game.field) field_out = [[1, -1, -1], [1, 1, 0], [-1, -1, -1]] assert np.array_equal(game.field, field_out)
def run_acquire_game(self, number_of_turns): """ Arguments: number_of_turns - the list of turns for the game to play through Returns: a generator which lists all the turns in a game and the GameOverReason ex: [start_state, state_2 ... state_n-1, state_n, ALLSAFE] """ gs = GameState(self._get_player_names(), handout=choice) gt = GameTree(gs) #send all initial player name/tile data to all players map(lambda (_, player): player.setup(deepcopy(gs)), self.players) yield gt.game_state turns_played = 0 while turns_played < number_of_turns: # grab the current Player from the list of Players name, current_player = self.players[0] # is the game over? ie, can we play any tiles? if self.is_game_over(gt.game_state, True): self.send_scores(gt.game_state) yield self.is_game_over(gt.game_state, True) return sell_back = {} keeps_cheaters = [] merger_happened = Box(False) current_player_cheated = Box(False) merger_placement = Box((None, None)) def merger_function(tile, hotel): """ Function handed to players to inform the administrator of a merge. Arguments: tile, hotel - tile and acquiring hotel Contract: Placing these results in a legal merge on the current game state. tile is owned by the current player Returns: state, [GameStatePlayer] - The GameState where other players have sold the stocks they intend to sell and a list of players """ state = deepcopy(gt.game_state) if merger_happened.get(): # this function has already been called current_player_cheated.set(True) return state, {} # kick! elif not state.board.valid_merge_placement(tile, hotel) or sell_back: current_player_cheated.set(True) return state, {} # kick! else: merger_happened.set(True) merger_placement.set((tile, hotel)) acquirees = state.board.acquirees(tile, hotel) players_with_keeps = {} for _, p in self.players: try: players_with_keeps[p] = p.keep(deepcopy(state), acquirees) except Exception as e: keeps_cheaters.append(p) # Deal with cheaters (the jerks) # => local functions keeps_cheaters.extend([p for p, ks in players_with_keeps.items() if len(ks) != len(acquirees)]) [remove_from_state(state, p) for p in keeps_cheaters] players_with_keeps = [(p, ks) for p, k in players_with_keeps.items() if p not in keeps_cheaters] # Function which given [True, False True] if acquirees are [C,A,T], returns [A] keeps_to_acquirees = lambda keeps: [h for h, k in zip(acquirees, keeps) if not k] # saves player keep data for the administrator for player, keeps in players_with_keeps: sell_back[player.id] = keeps_to_acquirees(keeps) if current_player in keeps_cheaters: current_player_cheated.set(True) return state, {} # KICK! state.place_a_tile(tile, hotel) map(lambda p: state.sellback(p, sell_back[p], gt.game_state), sell_back.keys()) return state, [state.player_with_name(p.id) for p, k in players_with_keeps if any(k)] try: tile, maybeHotel, shares = current_player.take_turn(deepcopy(gt.game_state), merger_function) except Exception as e: current_player_cheated = True for p in keeps_cheaters: print "cheating in keeps ", turns_played, p.id gt = self.kick(p, gt) # the current player is cheating! The bastard >:( # what to do in the case of the player trying to make an illegal merger # which causes other players to seem like they're cheating? # Also check that if player called merger placement if current_player_cheated.get() \ or (tile, maybeHotel) not in gt.get_tile_moves() \ or (merger_happened.get() and (tile, maybeHotel) != merger_placement.get()) \ or shares not in gt.get_share_moves(tile, maybeHotel, sell_back) \ or current_player in keeps_cheaters: print "cheating in take_turn", turns_played, current_player.id gt = self.kick(current_player, gt) continue new_tile = choice(gt.get_next_tiles()) current_player.new_tile(new_tile) gt = gt.apply(tile, maybeHotel, sell_back, shares, new_tile) # finish the round and ensure that our list of Players # is in sync with gs's players yield gt.game_state # check to see if the game is over again, # now that the current player has taken his turn if self.is_game_over(gt.game_state, False): self.send_scores(gt.game_state) yield self.is_game_over(gt.game_state, False) return for _, p in copy(self.players): try: p.inform(deepcopy(gt.game_state)) except Exception as e: gt = self.kick(p, gt) self.players.rotate(-1) # TODO: name this "CLOCKWISE" turns_played += 1 self.send_scores(gt.game_state) yield GameOverReason.OUTOFTURNS
def main(ai: str) -> None: """ This is the main function that allows for a user to play against an AI of their choice Preconditions: - ai == '1' or ai == '2' """ board = Board() g = GameTree(board) p1 = HumanPlayer(g) p2 = Player(g) if ai == '1': p2 = RandomPlayer(g) elif ai == '2': p2 = MiniMaxPlayer(3, False) else: print('This is not a valid input') exit() while len(board.get_valid_moves()) != 0: board.draw_board(WIN) board.draw_pieces(WIN) pygame.display.update() # L Piece Red Move valid_moves = board.get_valid_moves() new_board = p1.make_move(valid_moves, board.board, 'red') board.previous_boards.append(board.board) board.move_type = 'black' board.board = new_board board.draw_pieces(WIN) pygame.display.update() # Neutral Piece Red Move yn = input( 'Would you like to move a neutral piece? "Y" for yes, "N" for no') if yn == "Y": valid_moves = board.get_valid_moves() coords = p1.select_square() new_board = p1.move_neutral(valid_moves, board.board, coords) board.previous_boards.append(board.board) board.board = new_board board.draw_pieces(WIN) pygame.display.update() board.move_type = 'blue' # L Piece Blue Move valid_moves = board.get_valid_moves() new_board = p2.make_move(board) board.previous_boards.append(board.board) board.move_type = 'black' pygame.time.wait(1000) board.board = new_board board.draw_pieces(WIN) pygame.display.update() # Neutral Piece Blue Move valid_moves = board.get_valid_moves() new_board = p2.make_move(board) board.previous_boards.append(board.board) board.move_type = 'red' pygame.time.wait(1000) board.board = new_board board.draw_pieces(WIN) pygame.display.update() # Checks and prints winner if len(board.get_valid_moves()) == 0: winner = board.is_red_move if winner == 'red': print('Blue has won the game!') elif winner == 'blue': print('Red has won the game!')
def main(): end = True firstMove = True tree = None grid = [['e' for x in range(0,15)] for x in range(0,15)] occupied = set() while (end): presenceGo() if os.path.exists("end_game"): end = False break opponent_move = read_move() if opponent_move is not None and firstMove is False: occupied.add((opponent_move[2], opponent_move[1])) if firstMove is True: firstMove = False tree = GameTree(True, 7, 7) grid[7][7] = 'o' write_move(7,7) occupied.add((7,7)) else: best_value, chosen_state, actions = minimax(tree.root, -float('inf'), float('inf'), True, 2, occupied) x = 0 y = 0 heuristic3 = list() heuristic2 = list() heuristic1 = list() heuristic0 = list() move_coord = None for action in actions: x = action[0] y = action[1] new_grid = copy.deepcopy(grid) if new_grid[x][y] is 'e': new_grid[x][y] = 'o' heuristic, coordinate = evaluate(new_grid) if heuristic > -1: if heuristic is 0: heuristic0.append(coordinate) if heuristic is 1: heuristic1.append(coordinate) if heuristic is 2: heuristic2.append(coordinate) if heuristic is 3: heuristic3.append(coordinate) if len(heuristic0) > 0: move_coord= heuristic0[0] if len(heuristic1) > 0: move_coord= heuristic1[0] if len(heuristic2) > 0: move_coord= heuristic2[0] if len(heuristic3) > 0: move_coord= heuristic3[0] break_flag = False if move_coord is None: for x in range(0, 15): if break_flag is True: break for y in range(0, 15): if grid[x][y] is 'e': break_flag = True write_move(x, y) grid[x][y] = 'o' break else: tree.root = chosen_state write_move(move_coord[0],move_coord[1]) occupied.add((move_coord[0],move_coord[1]))
def parse_script(contents: str) -> GameTree: # TODO: this should parse multiple scenes. rest, scene = parse_scene(contents) if consume_space(rest) != '': raise ValueError('Malformed GameTree') return GameTree(scene)
def __init__(self): random.seed() self.game_tree = GameTree()