Thread: TIc tac toe from a 3x3 to a 4x4

  1. #1
    Registered User
    Join Date
    Jan 2012
    Posts
    4

    TIc tac toe from a 3x3 to a 4x4

    Ok so i can convert the board to a 4x4 but my problem is that i want the winner to connect 4 in a row. At the moment 3 in a row is the winner. Now i can't find the function where to modify this.
    Can anyone find this for me or even better show me how to modify the little section.


    Code:
    #include <iostream>
    #include <string>
    #include <cctype>
    
    using std::cout;
    using std::cin;
    using std::endl;
    
    using std::string;
    
    using std::tolower;
    
    class tttboard {
    private:
        char board[3][3];
    public:
        static const char NOBODY = ' ', PLAYER1 = 'X', PLAYER2 = 'O';
    
        tttboard();
        void init_board();
        void display();
        void set(int x, int y, char c);
        char get(int x, int y) const;
    };
    
    tttboard::tttboard() {
        init_board();
    }
    
    void tttboard::init_board() {
        for(int x = 0; x < 3; x ++) {
            for(int y = 0; y < 3; y ++) {
                board[x][y] = NOBODY;
            }
        }
    }
    
    void tttboard::display() {
        cout << endl;
    
        for(int y = 0; y < 3; y ++) {
            for(int x = 0; x < 3; x ++) {
                cout << board[x][y];
                if(x < 2) cout << '|';
            }
            
            cout << endl;
            if(y < 2) cout << "-+-+-\n";
        }
    }
    
    void tttboard::set(int x, int y, char c) {
        board[x][y] = c;
    }
    
    char tttboard::get(int x, int y) const {
        return board[x][y];
    }
    
    class opponent {
    private:
        string name;
    protected:
        char c;
        void set_name(string name, char c);
    public:
        virtual void move(const tttboard &board, int &xpos, int &ypos) = 0;
        string get_name() { return name; }
    };
    
    void opponent::set_name(string name, char c) {
        this->name = name + " (" + c + ")";
        this->c = c;
    }
    
    class aiopponent : public opponent {
    private:
        int two(char c, char x, char y, char z);
    public:
        aiopponent(string name, char c);
        void move(const tttboard &board, int &xpos, int &ypos);
    };
    
    aiopponent::aiopponent(string name, char c) {
        set_name(name, c);
    }
    
    /* Extremely simple AI that picks the next available spot.
    void aiopponent::move(const tttboard &board, int &xpos, int &ypos) {
        for(int x = 0; x < 3; x ++) {
            for(int y = 0; y < 3; y ++) {
                if(board.get(x, y) == tttboard::NOBODY) {
                    xpos = x, ypos = y;
                    cout << "AI picks position (" << x << ',' << y << ")\n";
                    return;
                }
            }
        }
    }*/
    
    int aiopponent::two(char c, char x, char y, char z) {
        if(x == c && y == c && z == tttboard::NOBODY) return 3;
        if(x == c && y == tttboard::NOBODY && z == c) return 2;
        if(x == tttboard::NOBODY && y == c && z == c) return 1;
        
        return 0;
    }
    
    void aiopponent::move(const tttboard &board, int &xpos, int &ypos) {
        int r;
        char ic;// = (c == tttboard::PLAYER1 ? tttboard::PLAYER2 : tttboard::PLAYER1);
        
        if(c == tttboard::PLAYER1) ic = tttboard::PLAYER2;
        else ic = tttboard::PLAYER1;
    
        /* Look for winning spots */
        for(int x = 0; x < 3; x ++) {
            if((r = two(c, board.get(0, x), board.get(1, x), board.get(2, x)))) {
                ypos = x, xpos = r-1;
                return;
            }
            
            if((r = two(c, board.get(x, 0), board.get(x, 1), board.get(x, 2)))) {
                xpos = x, ypos = r-1;
                return;
            }
        }
        
        if((r = two(c, board.get(0, 0), board.get(1, 1), board.get(2, 2)))) {
            xpos = r-1, ypos = r-1;
            return;
        }
        
        if((r = two(c, board.get(2, 0), board.get(1, 1), board.get(0, 2)))) {
            xpos = 3-r, ypos = r-1;
            return;
        }
        
        /* Block losing spots */
        for(int x = 0; x < 3; x ++) {
            if((r = two(ic, board.get(0, x), board.get(1, x), board.get(2, x)))) {
                ypos = x, xpos = r-1;
                return;
            }
            
            if((r = two(ic, board.get(x, 0), board.get(x, 1), board.get(x, 2)))) {
                xpos = x, ypos = r-1;
                return;
            }
        }
        
        if((r = two(ic, board.get(0, 0), board.get(1, 1), board.get(2, 2)))) {
            xpos = r-1, ypos = r-1;
            return;
        }
        
        if((r = two(ic, board.get(2, 0), board.get(1, 1), board.get(0, 2)))) {
            xpos = 3-r, ypos = r-1;
            return;
        }
        
        /* Pick the middle if it's available */
        if(board.get(1, 1) == tttboard::NOBODY) {
            xpos = 1, ypos = 1;
            return;
        }
        
        /* Take a corner if we don't have one yet */
        if(board.get(0, 0) != c && board.get(2, 0) != c 
            && board.get(0, 2) != c && board.get(2, 2) != c) {
            
            if(board.get(0, 0) == tttboard::NOBODY) {
                xpos = 0, ypos = 0;
                return;
            }
            if(board.get(2, 0) == tttboard::NOBODY) {
                xpos = 2, ypos = 0;
                return;
            }
            if(board.get(0, 2) == tttboard::NOBODY) {
                xpos = 0, ypos = 2;
                return;
            }
            if(board.get(2, 2) == tttboard::NOBODY) {
                xpos = 2, ypos = 2;
                return;
            }
        }
        
        /* Pick the next available spot */
        for(int x = 0; x < 3; x ++) {
            for(int y = 0; y < 3; y ++) {
                if(board.get(x, y) == tttboard::NOBODY) {
                    xpos = x, ypos = y;
                    return;
                }
            }
        }
    }
    
    class humanopponent : public opponent {
    public:
        humanopponent(char c);
        void move(const tttboard &board, int &xpos, int &ypos);
    };
    
    humanopponent::humanopponent(char c) {
        cout << "\nEnter your name: ";
        string name;
        cin >> name;
        set_name(name, c);
    }
    
    void humanopponent::move(const tttboard &board, int &xpos, int &ypos) {
        for(;;) {
            cout << "Enter column (x-axis) number (1-3): ";
            while(!(cin >> xpos) || xpos <= 0 || xpos > 3) {
                // !!!
                cin.clear();
                cout << ": ";
            }
            
            cout << "Enter row (y-axis) number (1-3): ";
            while(!(cin >> ypos) || ypos <= 0 || ypos > 3) {
                cin.clear();
                cout << ": ";
            }
            
            xpos --, ypos --;
            
            if(board.get(xpos, ypos) != tttboard::NOBODY) {
                cout << "That spot's already taken\n";
                continue;
            }
            
            break;
        }
    }
    
    class ttt {
    private:
        tttboard board;
        opponent *player[2];
        int turn;
    
    public:
        ttt();
        ~ttt();
        bool new_game();
        void play_game();
        int game_done();
    };
    
    ttt::ttt() : turn(0) {
        player[0] = player[1] = 0;
    }
    
    ttt::~ttt() {
        for(int x = 0; x < 2; x ++) {
            if(player[x]) delete player[x];
        }
    }
    
    bool ttt::new_game() {
        cout << "\nNew game\nEnter the type of player #1 ([A]I/[H]uman/[Q]uit): ";
        
        char one;
        for(;;) {
            if(!(cin >> one)) {
                cin.clear();
                continue;
            }
            
            one = tolower(one);
            if(one == 'q') return false;
            if(one == 'a' || one == 'h') break;
        }
        
        cout << "Enter the type of player #2 ([A]I/[H]uman/[Q]uit): ";
        
        char two;
        for(;;) {
            if(!(cin >> two)) {
                cin.clear();
                continue;
            }
            
            two = tolower(two);
            if(two == 'q') return false;
            if(two == 'a' || two == 'h') break;
        }
        
        if(one == 'h') player[0] = new humanopponent(tttboard::PLAYER1);
        else {
            player[0] = new aiopponent(
                "AI for player #1", tttboard::PLAYER1);
        }
        
        if(two == 'h') player[1] = new humanopponent(tttboard::PLAYER2);
        else {
            player[1] = new aiopponent(
                "AI for player #2", tttboard::PLAYER2);
        }
        
        turn = 0;
        play_game();
    
        return true;
    }
    
    void ttt::play_game() {
        int x, y, won;
        char again;
        
        do {
            board.init_board();
            
            while(!(won = game_done())) {
                board.display();
                cout << player[turn]->get_name() << endl;
                player[turn]->move(board, x, y);
                cout << player[turn]->get_name() << " picked position "
                    << x+1 << ", " << y+1 << endl;
                board.set(x, y, turn ? tttboard::PLAYER2 : tttboard::PLAYER1);
                turn = !turn;
            }
            
            board.display();
            cout << "Game over. ";
            
            switch(won) {
            case -1: cout << "Tie."; break;
            case 1: cout << player[0]->get_name() << " won!"; break;
            case 2: cout << player[1]->get_name() << " won!"; break;
            }
            
            cout << endl;
            
            cout << "Another round? ";
            cin >> again;
        } while(tolower(again) == 'y');
    }
    
    int ttt::game_done() {
        int n, flag = 0;
    
        for(int x = 0; x < 3 && !flag; x ++) {
            for(int y = 0; y < 3 && !flag; y ++) {
                if(board.get(x, y) == tttboard::NOBODY) flag = 1;
            }
        }
        
        if(!flag) return -1;
        
        for(int x = 0; x < 3; x ++) {
            if((n = board.get(x, 0)) != tttboard::NOBODY) {
                if(n == board.get(x, 1) && n == board.get(x, 2)) {
                    return n == tttboard::PLAYER1 ? 1 : 2;
                }
            }
        }
        
        for(int y = 0; y < 3; y ++) {
            if((n = board.get(0, y)) != tttboard::NOBODY) {
                if(n == board.get(1, y) && n == board.get(2, y)) {
                    return n == tttboard::PLAYER1 ? 1 : 2;
                }
            }
        }
        
        if((n = board.get(0, 0)) != tttboard::NOBODY) {
            if(n == board.get(1, 1) && n == board.get(2, 2)) {
                return n == tttboard::PLAYER1 ? 1 : 2;
            }
        }
        
        if((n = board.get(2, 0)) != tttboard::NOBODY) {
            if(n == board.get(1, 1) && n == board.get(0, 2)) {
                return n == tttboard::PLAYER1 ? 1 : 2;
            }
        }
        
        return 0;
    }
    
    int main() {
        cout << "ttt45 by DWK\n"
            "Simple Tic-Tac-Toe game.\n";
    
        ttt tictactoe;
        
        while(tictactoe.new_game());
    
        return 0;
    }

  2. #2

  3. #3
    Registered User
    Join Date
    Jan 2012
    Posts
    4
    tic-tac-toe computer

    if your having trouble reading my copy/paste attempt the original code is here

  4. #4
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    Your teacher will never believe you wrote this program.

  5. #5
    Registered User
    Join Date
    Jan 2012
    Posts
    4
    Teacher? im 26. Just wanted to play different sized boards. Never mind pen and paper will do.

  6. #6
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    I believe you. I REALLY DO!!!!

  7. #7
    Registered User
    Join Date
    Jan 2012
    Posts
    4
    You've got problems. When was the last time you had a girlfriend... never

  8. #8
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    Keep going - you're managing 1 step per post at the moment.
    5 1/2 steps to get others to doing your homework

    If you want to make a start, begin with declaring
    const int boardSize = 3;

    Then go through the code and replace anything which looks like a 3 indicating the board size, and replace it with the constant.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  9. #9
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    Quote Originally Posted by Jessica85 View Post
    You've got problems.
    You're a plagiarist.
    Quote Originally Posted by Jessica85 View Post
    When was the last time you had a girlfriend... never
    Now THAT sounds like a 26-year-old thing to say! But it is true that my wife won't let me have girlfriends.

  10. #10
    Registered User rogster001's Avatar
    Join Date
    Aug 2006
    Location
    Liverpool UK
    Posts
    1,472
    Now THAT sounds like a 26-year-old thing to say! But it is true that my wife won't let me have girlfriends.
    Touche.. Seems that some stereotypes about programmers die hard innit
    Thought for the day:
    "Are you sure your sanity chip is fully screwed in sir?" (Kryten)
    FLTK: "The most fun you can have with your clothes on."

    Stroustrup:
    "If I had thought of it and had some marketing sense every computer and just about any gadget would have had a little 'C++ Inside' sticker on it'"

Popular pages Recent additions subscribe to a feed