Python Forum
TicTacToe Game Add Exception Handling and Warning Function
Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
TicTacToe Game Add Exception Handling and Warning Function
#1
I built a TicTacToe game in Python, but I want to add exception handling in it And i also want to create a warning function which shows the position is filled try another position and it also shows if the player1 insert the position 1 and 9 then it'll show alert msg to player2 that if you'll not insert on 5 position then the player1 will won


    from IPython.display import clear_output
        def tictactoe():
            print("Game is Starting")
            play_again = True                    #While loop for play again
            while play_again:
                clear_output()                   #Function for clear output 
            
                board = ['p',' ',' ',' ',' ',' ',' ',' ',' ',' '] # make board and 
        							      storing all the 
        							      positions in a 
        							      list
        
        
        
                player = 1
                     
                print("player",player,"Select your marker") #Asking player to select 
        							marker
                marker = input()                            #set player marker's 
        						       input in a variable 
        						       'marker' 
        
        
                player_1, player_2 = set_marker(marker)     #set marker
                while True:    #while loop for taking a inputs from user
                    if player > 2:
                        player = 1
                
                    print("Player",player,": Enter your position")   #Asking to 
        								player enter the 
        								position
        
                    pos = int(input())      #typecasting
                    if check_pos(pos, board):#check position has been filled or not 
        					if this position has been filled then 
        					continue
        
                        continue
                    if player == 1:
                        set_board(board,player_1,pos)  #setting player1's marker
                    else:
                        set_board(board,player_2,pos)#setting player 2's marker
                        
                    display(board)    #display board
                    if player == 1:
                        if check_win(board, player_1): #will return boolean value
                            print("Player",player,"has won")
                            break
                    else:
                        if check_win(board, player_2):
                            print("Player",player,"has won")
                            break
                            
                    if check_space(board): # check space on board if there is no 
        				      space then game will draw
        			
                             print("Draw !!!")
                        break
                    player +=1 
                    
                             
                if replay(): # Play again
                    play_again = True
                
                    
        In [19]:
        def set_marker(marker):
            if marker=="X":
                return("X","O")
            else:
                return("O","X")
            
        def check_pos(pos, board):#check position
            if board[pos] == " ":# board is a list so check the position is empty or not if it is empty then return false
                return False
            else:
                return True
            
        
        def set_board(board,marker,pos):#here marker is a player
            board[pos] = marker
            
        def display(board):#display board
            clear_output()
            print(f'{board[7]} | {board[8]} | {board[9]}')
            print("----------------------------")
            print(f'{board[4]} | {board[5]} | {board[6]}')
            print("----------------------------")
            print(f'{board[1]} | {board[2]} | {board[3]}')
            print("----------------------------")
            
             
        def check_win(board, marker):
            return((board[1] == marker and board[2] == marker and board[3] == marker) or 
                   (board[4] == marker and board[5] == marker and board[6] == marker) or 
                   (board[7] == marker and board[8] == marker and board[9] == marker) or 
                   (board[9] == marker and board[5] == marker and board[1] == marker) or 
                   (board[7] == marker and board[5] == marker and board[3] == marker) or 
                   (board[7] == marker and board[4] == marker and board[1] == marker) or
                   (board[8] == marker and board[5] == marker and board[2] == marker) or 
                   (board[9] == marker and board[6] == marker and board[3] == marker))
        
        
        def check_space(board):
            if " "in board:
                return False
            else:
                return True
            
            
            
        def replay():    
            print("Do you want to play again Yes/No")
            ans = input()
            if ans == "Yes" or ans =="yes":
                return True
            else:
                return False
        In [15]:
        tictactoe()
Gribouillis write Nov-01-2021, 04:03 PM:
Please post all code, output and errors (it it's entirety) between their respective tags. Refer to BBCode help topic on how to post. Use the "Preview Post" button to make sure the code is presented as you expect before hitting the "Post Reply/Thread" button.
Reply
#2
I am having an error how resolve this

import pyodbc
import datetime
conn = pyodbc.connect('Driver={SQL Server};'
                      'Server=DESKTOP-MBJNNJR;'
                      'Database=master;'
                      'Trusted_Connection=yes;')
cursor = conn.cursor()

cursor.execute('SELECT Employee_Name, Hire_Date FROM Employee WHERE Hire_Date BETWEEN [{%s}] AND [{%s}]')
hire_start = datetime.date(1999, 1, 1)
hire_end = datetime.date(1999, 12, 31)
cursor.execute(query, (hire_start, hire_end))
for (Employee_Name, Hire_Date) in cursor:

    print("{}, {} was hired on {:%d %m %Y}".format(Employee_Name, Hire_Date))
cursor.close()
Error:
ProgrammingError: ('42S22', "[42S22] [Microsoft][ODBC SQL Server Driver][SQL Server]Invalid column name '{%s}'. (207) (SQLExecDirectW); [42S22] [Microsoft][ODBC SQL Server Driver][SQL Server]Invalid column name '{%s}'. (207)")
Yoriz write Nov-02-2021, 03:17 PM:
Please post all code, output and errors (in their entirety) between their respective tags. Refer to BBCode help topic on how to post. Use the "Preview Post" button to make sure the code is presented as you expect before hitting the "Post Reply/Thread" button.
Reply
#3
You should not ask two completely different questions in the same thread. This is in response to your SQLite3 question. Do you have a column named %s?

I think instead of this:
cursor.execute('SELECT Employee_Name, Hire_Date FROM Employee WHERE Hire_Date BETWEEN [{%s}] AND [{%s}]')
hire_start = datetime.date(1999, 1, 1)
hire_end = datetime.date(1999, 12, 31)
cursor.execute(query, (hire_start, hire_end))
You want to do this:
query = 'SELECT Employee_Name, Hire_Date FROM Employee WHERE Hire_Date BETWEEN [{%s}] AND [{%s}]'
hire_start = datetime.date(1999, 1, 1)
hire_end = datetime.date(1999, 12, 31)
cursor.execute(query, (hire_start, hire_end))
I don't think you should be using the square brackets either.
And this is in response to the tic-tac-toe question.

Validation is required whenever you ask for user input. A common form of validation is to ask for input until the user provides valid input.
        while True:
            try:
                position = int(input(f"Player {player+1} Enter your position "))
            except ValueError:
                print("Positions are 1 through 9")
            else:
                if not 1 <= position <= 9:
                    print("Positions are 1 through 9")
                elif board[position] in markers:
                    print('Position was already chosen.')
                else:
                    break
First it checks if the input is a number, then it checks if the number is in range, and finally it checks if there is already a marker in that position.

How do your players know what the board positions are? I modified you program slightly to fill the board with numbers 1 through 9 so there is no guessing about where the marker is placed. I also separated the play again logic from the game logic and added auto-fill for the last empty position.
from IPython.display import clear_output

def display(b):
    '''Display the board'''
    clear_output()
    print(f' {b[1]} | {b[2]} | {b[3]}')
    print("---+---+---")
    print(f' {b[4]} | {b[5]} | {b[6]}')
    print("---+---+---")
    print(f' {b[7]} | {b[8]} | {b[9]}\n')

def check_win(b):
    '''Return True if the board contains a win, else False.'''
    return (
        (b[1] == b[2] == b[3]) or
        (b[4] == b[5] == b[6]) or
        (b[7] == b[8] == b[9]) or
        (b[1] == b[4] == b[7]) or
        (b[2] == b[5] == b[8]) or
        (b[3] == b[6] == b[9]) or
        (b[1] == b[5] == b[9]) or
        (b[3] == b[5] == b[7]))

def tictactoe():
    '''Play a game of tic-tac-toe'''
    # Let first player select their marker
    markers = 'XO'
    if input("Player 1 select your marker ").upper() == 'O':
        markers = 'OX'

    # Create and display empty board
    clear_output()
    board = [str(i) for i in range(10)]
    display(board)

    # Take turns letting players place their markers on the board.
    for i in range(8):
        player = i % 2
        # Get position for marker.  Must be integer value in range 1..9 and
        # selected position must be empty.
        while True:
            try:
                position = int(input(f"Player {player+1} Enter your position "))
            except ValueError:
                print("Positions are 1 through 9")
            else:
                if not 1 <= position <= 9:
                    print("Positions are 1 through 9")
                elif board[position] in markers:
                    print('Position was already chosen.')
                else:
                    break
        board[position] = markers[player]
        display(board)
        if check_win(board):
            return player+1

    # Only one empty position remains.  Auto fill and check for a winner
    for i, marker in enumerate(board):
        if marker not in markers:
            board[i] = markers[0]
    display(board)
    if check_win(board):
        return 1
    return 0

while True:
    # Play tic-tac-toe.  Report who wins.
    winner = tictactoe()
    if winner == 0:
        print("Draw!!")
    else:
        print(f"Player {winner} wins!")
    if input("Do you want to play again Y/N ").upper() != 'Y':
        break
Reply
#4
For tic tac toe, your best place for adding exception handling is where you get the user input for each turn. Surround that by a try except block to catch the input error where a person inputs "foo" instead of a number 1-9.

For the first warning you are halfway there, in that the if check_pos check will return whether the position is occupied or not. However, you don't do anything with that information - it continues anyway. You instead should loop back to get another value from the player.

There are lots of ways to look at the last question in tic tac toe. One option, that I would probably pursue, is to assign a value of -1 for X and +1 for O, then add across rows, columns, or diagonals (similar to how you determine a game over). If the sum is -2 or 2 then give the warning.

I defer to deanhystad on the second question and agree - don't ask 2 unrelated questions on a single thread.
Reply
#5
I think the easiest way to identify blocks is to try filling each square with the opponents marker and check if this results in a win.
    def analysis(board, X, O):
        '''Search for wins and blocks.  Player one is marker X and player 2 marker O'''
        for pos in range(1, 10):
            if not board[pos] in (X, O):
                board[pos] = X
                if winner(board):
                    print(f"Choose {pos} to  win")
                board[pos] = O
                if winner():
                    print(f"Choose {pos} to block")
                board[pos] = str(pos)
Reply
#6
Tic-tac-toe with hints, improved user input and auto-fill for the last open square.
# from IPython.display import clear_output

def clear_output():
    print("\n\n\n")

def display(board):
    '''Display the board'''
    clear_output()
    print(f" {board[1]} | {board[2]} | {board[3]}\n---+---+---")
    print(f" {board[4]} | {board[5]} | {board[6]}\n---+---+---")
    print(f" {board[7]} | {board[8]} | {board[9]}\n")

def winner(board):
    '''Return True if the board contains a win, else False.'''
    return (
        (board[1] == board[2] == board[3]) or
        (board[4] == board[5] == board[6]) or
        (board[7] == board[8] == board[9]) or
        (board[1] == board[4] == board[7]) or
        (board[2] == board[5] == board[8]) or
        (board[3] == board[6] == board[9]) or
        (board[1] == board[5] == board[9]) or
        (board[3] == board[5] == board[7]))

def analysis(board, markers):
    '''Inform player of winning and blocking moves'''
    for square in range(1, 10):
        if board[square] not in markers:
            # Check if filling an open square results in a win
            board[square] = markers[0] # For the player
            if winner(board):
                print(f"Choose {square} to win")
            board[square] = markers[1] # For the opponent
            if winner(board):
                print(f"Choose {square} to block")
            board[square] = str(square)

def tictactoe():
    '''Play a game of tic-tac-toe'''
    # Let player 1 select a marker
    clear_output()
    markers = 'XOX'  # Board markers, Player 1, Player 2, Player 1
    if input("Player 1 select your marker ").upper() == 'O':
        markers = 'OXO'

    # Create and display empty board
    board = [str(i) for i in range(10)]
    open_squares = list(range(1, 10))
    display(board)

    # Players take turns placing markers on the board.
    for i in range(8):
        player = i % 2
        marker = markers[player]
        # Get square for players marker
        analysis(board, markers[player:])  # Provide helpful hints
        while True:
            try:
                square = int(input(f"{marker} select square "))
                if square not in open_squares:
                    raise ValueError
            except ValueError:
                print(f"Available squares are {open_squares}")
            else:
                break
        board[square] = marker
        open_squares.remove(square)
        display(board)
        if winner(board):
            return player+1 # Return number of winning player (1 or 2)

    # One open square remains.  Fill and check for a winner
    board[open_squares[0]] = markers[0]
    display(board)
    if winner(board):
        return 1
    return 0 # Return game ends in draw

while True:
    # Play tic-tac-toe.  Report who wins.
    result = tictactoe()
    if result == 0:
        print("Draw!!")
    else:
        print(f"Player {result} wins!")
    if input("Do you want to play again Y/N ").upper() != 'Y':
        break
Reply


Possibly Related Threads…
Thread Author Replies Views Last Post
Star python exception handling handling .... with traceback mg24 3 1,285 Nov-09-2022, 07:29 PM
Last Post: Gribouillis
  create my exception to my function korenron 2 797 Nov-09-2022, 01:50 PM
Last Post: korenron
  Array in tictactoe machine not working? Illumimint 4 1,626 Jun-02-2022, 02:24 AM
Last Post: Illumimint
  Exception handling in regex using python ShruthiLS 1 2,370 May-04-2020, 08:12 AM
Last Post: anbu23
  Exception handling Calli 2 2,471 Apr-20-2020, 06:13 PM
Last Post: Calli
  TicTacToe PC vs PC harig3 3 2,281 Mar-28-2020, 01:13 PM
Last Post: harig3
  Handling exception from a module dchi2 11 5,629 Nov-25-2019, 08:47 AM
Last Post: dchi2
  problem using custom exception handling in python srm 3 3,067 Jul-03-2019, 09:10 PM
Last Post: ichabod801
  an easy way to disable exception handling Skaperen 6 5,476 Jun-02-2019, 10:38 PM
Last Post: Gribouillis
  exception handling KyawMyo 3 2,860 May-07-2019, 07:53 AM
Last Post: buran

Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020