generated from mwc/lab_tic_tac_toe
50 lines
2.1 KiB
Python
50 lines
2.1 KiB
Python
class NimGame:
|
|
"""A Nim game class based off NimGameStub.
|
|
"""
|
|
def get_initial_state(self):
|
|
''' Constructs the game board and has player 1 start the game. '''
|
|
return {
|
|
"board": [1, 3, 5, 7],
|
|
"first_player": True
|
|
}
|
|
|
|
def get_next_state(self, state, action):
|
|
''' Creates a copy of the current board and then makes adjustments
|
|
based on the chosen action from a player's turn. '''
|
|
new_board = state["board"].copy()
|
|
new_board[action[0]] = new_board[action[0]] - action[1]
|
|
return {
|
|
"board": new_board,
|
|
"first_player": not state["first_player"],
|
|
}
|
|
|
|
def get_actions(self, state):
|
|
''' Construct the list of actions that can be taken by a player.
|
|
Is there a more efficient way of doign this? '''
|
|
actions = []
|
|
new_board = state["board"].copy()
|
|
for i in range(4): # check the four rows of the board
|
|
if new_board[i] > 0: # if a row is not empty
|
|
for j in range(1,4): # check if you can remove 1, 2, or 3 ticks in the row
|
|
if j <= new_board[i]: # if so
|
|
actions.append((i,j)) # include that as an option
|
|
return actions
|
|
|
|
def get_reward(self, state):
|
|
''' Reports who wins. '''
|
|
if state["first_player"]:
|
|
return 1 # If it is the player's turn and there is nothing on the board, then it was the robot who crossed off the last line.
|
|
return 0 # Otherwise, the first player made the last move and lost.
|
|
|
|
def is_over(self, state):
|
|
''' Reports true if there are no more lines to cross. '''
|
|
if all(ticks == 0 for ticks in state["board"]):
|
|
return True
|
|
return False
|
|
|
|
def get_objective(self, state):
|
|
''' Reports the desired obejctive to help choose the move that
|
|
yields the optimal reward under the lookahead_strategy for
|
|
computer players. '''
|
|
return max if state["first_player"] else min
|