Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- ttt.h
- __
- // ttt.h
- #ifndef TTT_H
- #define TTT_H
- #include <tuple>
- #include <array>
- #include <vector>
- #include <ctime>
- #include <random>
- #include <iterator>
- #include <iostream>
- #include <utility>
- enum class Player { X, O, None };
- using Move = int;
- using State = std::array<Player,9>;
- using MoveEval = std::pair<Move,int>;
- // used to get a random element from a container
- template<typename Iter, typename RandomGenerator>
- Iter select_randomly(Iter start, Iter end, RandomGenerator& g) {
- std::uniform_int_distribution<> dis(0, std::distance(start, end) - 1);
- std::advance(start, dis(g));
- return start;
- }
- template<typename Iter>
- Iter select_randomly(Iter start, Iter end) {
- static std::random_device rd;
- static std::mt19937 gen(rd());
- return select_randomly(start, end, gen);
- }
- std::ostream &operator<<(std::ostream &os, const State &state);
- std::ostream &operator<<(std::ostream &os, const Player &player);
- Player getCurrentPlayer(const State &state);
- State doMove(const State &state, const Move &m);
- Player getWinner(const State &state);
- std::vector<Move> getMoves(const State &state);
- #endif // TTT_H
- ___
- main.cpp
- ___
- // ttt_ab.cpp
- // Compile with: g++ -std=c++11 -o ttt_ab ttt_ab.cpp ttt.cpp
- #include <iostream>
- #include <algorithm>
- #include <map>
- #include <limits>
- #include "ttt.h"
- enum class PlayerType { Human, Computer };
- Move choice;
- int eval(const State &board, const Player &player, int ply)
- {
- if(getWinner(board) == player){
- return 500 + 10 * ply;
- }
- if(getWinner(board) != player && getWinner(board) != Player::None){
- return -500 - 10 * ply;
- }
- if(getWinner(board) == Player::None){
- return 0;
- }
- }
- MoveEval alphaBeta(State &board, int ply, Player player, Player opponent, int alpha, int beta)
- {
- State trialboard = board;
- if (ply == 0)
- return std::make_pair(Move(), eval(trialboard, player, ply));
- std::vector<Move> moves = getMoves(trialboard);
- if (moves.size() == 0)
- return std::make_pair(Move(), eval(trialboard, player, ply));
- MoveEval best = std::make_pair(Move(),alpha);
- for (Move &move: moves) {
- trialboard = doMove(trialboard, move);
- MoveEval me = alphaBeta(trialboard, ply - 1, opponent, player, -beta, -alpha);
- trialboard = board;
- if (-me.second > alpha) {
- alpha = -me.second;
- best = std::make_pair(move,alpha);
- }
- if (alpha >= beta)
- return best;
- }
- return best;
- }
- Move alphaBeta(const State &b, int ply)
- {
- State board = b;
- Player player = Player::O;
- Player opponent = Player::X;
- return alphaBeta(board, ply, player, opponent, std::numeric_limits<int>::min() + 1, std::numeric_limits<int>::max()).first;
- }
- int main()
- {
- std::srand(std::time(0));
- std::map<Player,PlayerType> playerType;
- playerType[Player::X] = PlayerType::Human;
- playerType[Player::O] = PlayerType::Computer;
- State board = {
- Player::None, Player::None, Player::None,
- Player::None, Player::None, Player::None,
- Player::None, Player::None, Player::None };
- std::cout << board << std::endl;
- std::vector<Move> moves = getMoves(board);
- while (moves.size() > 0) {
- if (playerType[getCurrentPlayer(board)] == PlayerType::Human) {
- std::cout << "+-+-+-+" << std::endl <<
- "|0|1|2|" << std::endl <<
- "+-+-+-+" << std::endl <<
- "|3|4|5|" << std::endl <<
- "+-+-+-+" << std::endl <<
- "|6|7|8|" << std::endl <<
- "+-+-+-+" << std::endl << std::endl;
- std::cout << "Enter a move ( ";
- for (Move m: moves) std::cout << m << " ";
- std::cout << "): ";
- Move m;
- std::cin >> m;
- board = doMove(board, m);
- } else {
- board = doMove(board, alphaBeta(board, 9));
- }
- std::cout << board << std::endl;
- moves = getMoves(board);
- }
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement