Java code

Tic Tac Toe game in Java

This is an example of using nested while loops, char arrays and if statements. Please note this is based on tutorial by Alex Lee. However, a modification was made to the code to remove a bug. The original code by the author would allow the player to place the position on top of the CPU position. Please subscribe to Alex’s YouTube channel and support him.



Complete code

public class TicTacToe {    
    static ArrayList<Integer> playerPositions = new ArrayList<Integer>();    
    static ArrayList<Integer> cpuPositions = new ArrayList<Integer>();
    
    public static void main (String [] args) {
        // Create a Scanner object attached to the keyboard
        Scanner scan = new Scanner (System.in);
        // Gameboard print
        char[][] gameBoard = {
                    {' ', '|', ' ', '|', ' '}, 
                    {'-', '+', '-', '+', '-'},
                    {' ', '|', ' ', '|', ' '},
                    {'-', '+', '-', '+', '-'},
                    {' ', '|', ' ', '|', ' '}};
        
        printGameBoard(gameBoard);
        
        //User input requests
        while(true) {
            System.out.println("Enter your placement (1-9):");
            int playerPos = scan.nextInt();
            while(playerPositions.contains(playerPos) || cpuPositions.contains(playerPositions) || cpuPositions.contains(playerPos)){
                System.out.println("Position taken! Enter another position:");
                playerPos = scan.nextInt();
                //Prevent user from printing on top of CPU
                while(playerPositions.contains(playerPos) || cpuPositions.contains(playerPos)){
                    System.out.println("Position taken! Enter another position:");
                    playerPos= scan.nextInt();
                }
            }
        
            placePiece(gameBoard, playerPos, "player");
            
            String result = checkWinner();
            if(result.length() > 0) {
                System.out.println(result);
                break;            
            }
            //CPU random positions
            Random rand = new Random();
            int cpuPos = rand.nextInt(9) + 1;
            while(playerPositions.contains(cpuPos) || cpuPositions.contains(cpuPos)){
                cpuPos = rand.nextInt(9) + 1;
            }
            
            placePiece(gameBoard, cpuPos, "cpu");
        
            printGameBoard(gameBoard);
            
            result = checkWinner();
            if(result.length() > 0){
                System.out.println(result);
                break;
            }
        }

          }
    public static void placePiece(char[][] gameBoard, int pos, String user){
        
        char symbol = ' ';
        
        if(user.equals("player")){
            symbol = 'X';
            playerPositions.add(pos);
        } else if(user.equals("cpu")){
            symbol = 'O';
            cpuPositions.add(pos);
        }

        switch(pos){
            case 1:
                gameBoard[0][0] = symbol;
                break;
            case 2:
                gameBoard[0][2] = symbol;
                break;
            case 3:
                gameBoard[0][4] = symbol;
                break;
            case 4:
                gameBoard[2][0] = symbol;
                break;
            case 5:
                gameBoard[2][2] = symbol;
                break;
            case 6:
                gameBoard[2][4] = symbol;
                break;
            case 7:
                gameBoard[4][0] = symbol;
                break;
            case 8:
                gameBoard[4][2] = symbol;
                break;
            case 9:
                gameBoard[4][4] = symbol;
                break;                          
            default:
                break;
        }
    }
    public static String checkWinner(){        
        List topRow = Arrays.asList(1, 2, 3);
        List midRow = Arrays.asList(4, 5, 6);
        List botRow = Arrays.asList(7, 8, 9);
        List leftCol = Arrays.asList(1, 4, 7);
        List midCol = Arrays.asList(2, 5, 8);
        List rightCol = Arrays.asList(3, 6, 9);
        List cross1 = Arrays.asList(1, 5, 9);
        List cross2 = Arrays.asList(7, 5, 3);
        
        List<List> winning = new ArrayList<List>();
        winning.add(topRow);
        winning.add(midRow);
        winning.add(botRow);
        winning.add(leftCol);
        winning.add(midCol);
        winning.add(rightCol);
        winning.add(cross1);
        winning.add(cross2);
        
        for(List l : winning){
            if(playerPositions.containsAll(l)){
                return "Congraduations you won!";
            } else if(cpuPositions.containsAll(l)){
                return "CPU wins! Sorry!";
            } else if(playerPositions.size() + cpuPositions.size() == 9){
                return "We are tied!";
            }
        }
        
        return "";       
    }
    public static void printGameBoard (char [][] gameBoard){ 
        for(char[] row : gameBoard) {
            for(char c : row) {
                System.out.print(c);              
            }
            System.out.println();
        }
    }
}

Modification: The following code was modified from the original code to prevent the user from entering a position on top of the CPU position. The modification is inside the user input while loop.

            while(playerPositions.contains(playerPos) || cpuPositions.contains(playerPositions) || cpuPositions.contains(playerPos)){
                System.out.println("Position taken! Enter another position:");
                playerPos = scan.nextInt();
                //Prevent user from printing on top of CPU
                while(playerPositions.contains(playerPos) || cpuPositions.contains(playerPos)){
                    System.out.println("Position taken! Enter another position:");
                    playerPos= scan.nextInt();
                }
            }