This is based on my first Tic-Tac-Toe game:Tic-Tac-Toe in C++11I have come up with different game logic for my game. I would like to know which one is more reliable and effective and how I can improve the whole game.#include <iostream>#include <cctype>#include <algorithm>#include <functional>#include <array>#include <vector>class TicTacToe{public:    bool isFull() const;    void draw() const;    void turn(char player);    bool check(char player) const;private:    bool fill(char player, int position);    static const std::size_t mDim = 3;    std::array<char, mDim * mDim> grid    {         {               '-', '-', '-',            '-', '-', '-',            '-', '-', '-'         }     };};template<std::size_t dim>struct column : public std::unary_function<int, bool>{    column(int i)         : colNum(i)    {}    bool operator() (int number)     {         return (number % dim == colNum);     }    int colNum;};struct pairCondition{    int number;    char name;    pairCondition(int number, char name)        : number(number), name(name)    {}    bool operator== (const pairCondition& s) const    {        return name == s.name;    }};bool checkCondition(const pairCondition& i, const std::array<int, 3>& a, char player){    if (i.number == a[0] || i.number == a[1] || i.number == a[2])        return i.name == player;    else        return i.name != player;}bool TicTacToe::fill(char player, int position){    if (grid[position] != '-')        return false;    grid[position] = player;    return true;}bool TicTacToe::isFull() const{    return 0 == std::count_if(grid.begin(), grid.end(),        [](const char& i)    {        return i == '-';    });}bool TicTacToe::check(char player) const{    typedef std::function<bool(pairCondition)> func;    // rows    bool row1 = true, row2 = true, row3 = true;    std::array<int, 3> rows1 = { 0, 1, 2 };    std::array<int, 3> rows2 = { 3, 4, 5 };    std::array<int, 3> rows3 = { 6, 7, 8 };    func rowf1 = std::bind(&checkCondition, std::placeholders::_1, rows1, player);    func rowf2 = std::bind(&checkCondition, std::placeholders::_1, rows2, player);    func rowf3 = std::bind(&checkCondition, std::placeholders::_1, rows3, player);    // columns    bool col1 = true, col2 = true, col3 = true;    std::array<int, 3> columns1 = { 0, 3, 6 };    std::array<int, 3> columns2 = { 1, 4, 7 };    std::array<int, 3> columns3 = { 2, 5, 8 };    func colf1 = std::bind(&checkCondition, std::placeholders::_1, columns1, player);    func colf2 = std::bind(&checkCondition, std::placeholders::_1, columns2, player);    func colf3 = std::bind(&checkCondition, std::placeholders::_1, columns3, player);    // diagonals    bool diag1 = true, diag2 = true;    std::array<int, 3> diagonal1 = { 0, 4, 8 };    std::array<int, 3> diagonal2 = { 2, 4, 6 };    func diagf1 = std::bind(&checkCondition, std::placeholders::_1, diagonal1, player);    func diagf2 = std::bind(&checkCondition, std::placeholders::_1, diagonal2, player);    std::vector<pairCondition> v =    {        { 0, grid[0] }, { 1, grid[1] }, { 2, grid[2] },        { 3, grid[3] }, { 4, grid[4] }, { 5, grid[5] },        { 6, grid[6] }, { 7, grid[7] }, { 8, grid[8] }    };    for (const auto& i : v)    {        // rows conditions        row1 &= rowf1(i);        row2 &= rowf2(i);        row3 &= rowf3(i);        // columns conditions        col1 &= colf1(i);        col2 &= colf2(i);        col3 &= colf3(i);        // diagonals conditions        diag1 &= diagf1(i);        diag2 &= diagf2(i);    };    return (row1 || row2 || row3 ||            col1 || col2 || col3 ||            diag1 || diag2);}void TicTacToe::draw() const{    //Creating a onscreen grid    std::cout << ' ';    for (std::size_t i = 1; i <= mDim; ++i)        std::cout <<    << i;    int j = 0;    char A = 'A';    column<mDim>::argument_type input;    for (auto& i : grid)    {        if (column<mDim>(0)(input = j++))            std::cout << \n  << A++;        std::cout << ' ' << i << ' ';    }    std::cout << \n\n;}void TicTacToe::turn(char player){    char row = 0;    char column = 0;    std::size_t position = 0;    bool applied = false;    std::cout << \n << player << : Please play. \n;    while (!applied)     {        std::cout << Row(1,2,3,...): ;        std::cin >> row;        std::cout << player << : Column(A,B,C,...): ;        std::cin >> column;        position = mDim * (std::toupper(column) - 'A') + (row - '1');        if (position < grid.size())         {            applied = fill(player, position);            if (!applied)                std::cout << Already Used. Try Again. \n;        }        else         {            std::cout << Invalid position.  Try again.\n;        }    }    std::cout << \n\n;}class Game{public:    Game() = default;    void run();private:    TicTacToe ttt;    std::array<char, 2> players{ { 'X', 'O' } };    int player = 1;    void resultScreen();    std::function<void()>       display = std::bind(&TicTacToe::draw, &ttt);    std::function<void(char)>   turn    = std::bind(&TicTacToe::turn, &ttt, std::placeholders::_1);    std::function<bool(char)>   win     = std::bind(&TicTacToe::check, &ttt, std::placeholders::_1);    std::function<bool()>       full    = std::bind(&TicTacToe::isFull, &ttt);};void Game::run(){    while (!win(players[player]) && !full() )    {        player ^= 1;        display();        turn(players[player]);    }    resultScreen();}void Game::resultScreen(){    display();    if (win)    {        std::cout << \n << players[player] <<  is the Winner!\n;    }    else    {        std::cout << \nTie game!\n;    }}int main(){    Game game;    game.run();}
Tic-Tac-Toe in C++11 - follow-up
c++;game;c++11;tic tac toe
I have a few tidbits that could help. Nothing big, but things that you can improve as you code without having to overthink them:Use constexpr to represent compile-time constants. static const works but constexpr pops into to head and screams compile time! when you read it:static constexpr std::size_t mDim = 3;column::operator() should be const-qualified since it does not alter the state of column:bool operator() (int number) const{     return (number % dim == colNum); }unary_function and binary_function are deprecated since C++11 and will be removed from the standard in C++17. Therefore, you should avoid using them. The easy fix is to define result_type and argument_type by hand (which is rahter quick) or to simply use the types at the call point where you probably know them.You could consider making the types column and pairCondition immutable by making their members const. Beforehand, really think about whether you want them to be immutable. It could make sense for column since functions are often immutable and this is a functor type.I don't think that you want to represent any other cells thant no player, player 1 and player 2. Therefore, you could probably use an enum struct to represent the accepted values in your grid instead of a char:enum struct player: char{    none = '-',    first = 'X',    second = 'O'};Using an enum struct would ensure that you don't use any other magic value and would answer the question what does this char represent? when reading the code. If you really need to access the underlying type of the enum at different places, then use a simple enum instead of an enum struct.