I have designed a tic tac toe game and it is working fine when I play only a single game. But I am having trouble to implement replay functionality in it once 1st game is over successfully. I have declared player_position as global. It stores the values of the position of X and O after every move.
player_position={'X':[],'O':[]}
And I have made the tic tac toe table as follows:
def print_tic_tac_toe(values):
print("\n")
print("\t | |")
print("\t {} | {} | {}".format(values[0], values[1], values[2]))
print('\t_____|_____|_____')
print("\t | |")
print("\t {} | {} | {}".format(values[3], values[4], values[5]))
print('\t_____|_____|_____')
print("\t | |")
print("\t {} | {} | {}".format(values[6], values[7], values[8]))
print("\t | |")
print("\n")
Following is values variable defined and above function called:
values=[' ' for x in range(9)]
print_tic_tac_toe(values)
Then I have made the functions to check winning condition and draw condition after each move:
def winning_condition(player_position, current_player):
soln = [[0, 1, 2], [3, 4, 5], [6, 7, 8], [0, 3, 6], [1, 4, 7], [2, 5, 8], [0, 4, 8], [2, 4, 6]]
for x in soln:
if set(x).issubset(player_position[current_player]):
return True
return False
def draw_condition(player_position):
if (len(player_position['X'])+len(player_position['O'])==9):
return True
return False
Following is the replay function which is the main problem I am facing and want to know how to call it in my main function:
def replay():
play_again=input('Do you want to play again? y/n :')
return (play_again=='y')
Following is the main function:
import random
def start_game():
toss=random.randint(0,1)
print ('Toss result is: ',toss)
if toss==0:
current_player='X'
print ('X will go first')
else:
current_player='O'
print ('O will go first')
while True:
print_tic_tac_toe(values)
print ('Enter your position player ', current_player)
move=int(input())
if move<0 or move>8:
print('Position does not exist. Try again!!')
continue
if values[move]!=' ':
print('Position already occupied. Try again!!')
continue
values[move]=current_player
player_position[current_player].append(move)
if winning_condition(player_position, current_player):
print_tic_tac_toe(values)
print ('Congrats Player ', current_player, ' you have won the game')
print ('\n')
if not replay():
print ('Game Ended')
break
if draw_condition(player_position):
print_tic_tac_toe(values)
print ('Game Drawn')
print('\n')
if not replay():
print ('Game Ended')
break
if current_player=='X':
current_player='O'
else:
current_player='X'
Now I know replay function will be called when I am checking winning_condition and draw_condition inside start_game function. But I don't know how. What I want is when I call replay function, it should give me an empty tic tac toe table and consequently remove all the values of X and O from player_position. Following is the way to clear values of X and O from player_position when the game has ended:
for k in player_position:
player_position[k]=[]
But I don't know how to use it and how to get an empty tic tac toe table after first game has finished. Any help to help me design replay functionality in this code will be highly appreciated. Thanks.
Okay so a few things got changed. I rewrote your board printing function because it was messy and I felt like cleaning it up. I used unicode box-drawing characters, which you can get here.
Now the important stuff:
replay()
function now ensures proper input from the userreplay()
, meaning that the start_game()
function is exitedif __name__ == "__main__"
pattern, which you can read more about hereplayer_position
and values
variables are now entirely local to the start_game
function's scopeplayer_position
and values
variables are now initialized at the top of start_game()
so that when start_game()
is called, a new game is createdNow that you've got this under your belt, I'd suggest learning some basic OOP, and turning the game board into an object.
import random
def print_board(values):
s = """
\t . ┃ . ┃ .
\t━━━╋━━━╋━━━
\t . ┃ . ┃ .
\t━━━╋━━━╋━━━
\t . ┃ . ┃ .
"""
print(s.replace(".", "{}").format(*values))
def replay():
while True:
play_again = input("Do you want to play again? y/n :")
if play_again.lower() in ["y", "n"]:
return play_again.lower() == "y"
print("Invalid input!")
def winning_condition(player_position, current_player):
soln = [[0, 1, 2], [3, 4, 5], [6, 7, 8], [0, 3, 6], [1, 4, 7], [2, 5, 8], [0, 4, 8], [2, 4, 6]]
for x in soln:
if set(x).issubset(player_position[current_player]):
return True
return False
def draw_condition(player_position):
if (len(player_position["X"]) + len(player_position["O"]) == 9):
return True
return False
def start_game():
player_position={"X": [], "O": []}
values = [" " for x in range(9)]
toss = random.randint(0, 1)
print(f"Toss result is: {toss}")
if toss == 0:
current_player = "X"
else:
current_player = "O"
print(f"{current_player} will go first")
while True:
print_board(values)
move = int(input(f"Enter your position player {current_player}: "))
if move < 0 or move > 8:
print("Position does not exist. Try again!!")
continue
if values[move] != " ":
print("Position already occupied. Try again!!")
continue
values[move] = current_player
player_position[current_player].append(move)
if winning_condition(player_position, current_player):
print_board(values)
print(f"Congrats Player {current_player}, you have won the game!")
return replay()
elif draw_condition(player_position):
print_board(values)
print("Game Drawn!")
return replay()
if current_player == "X":
current_player = "O"
else:
current_player = "X"
if __name__ == "__main__":
play_again = True
while play_again:
play_again = start_game()
print("Thanks for playing!")
Here's what the game board looks like now:
X ┃ O ┃ X
━━━╋━━━╋━━━
O ┃ O ┃ X
━━━╋━━━╋━━━
O ┃ X ┃ O
It looks less gappy in the Python REPL.