CCF 井字棋

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/alegriabaile/article/details/79616820

CCF CSP13 (4) 井字棋 补了一天算法课后的尝试


涉及算法:极大极小算法。
未进行剪枝等优化操作。

C/C++ code:

#include<iostream>
using namespace std;

const int constX = 1;
const int constO = 2;

//return 1 if X win, -1 O win, 0 not decided or tied
int IsWin(const int chess[9])
{
    int mask[8][3] = { {0,1,2}, {3,4,5}, {6,7,8}, {0,3,6}, {1,4,7}, {2,5,8}, {0,4,8}, {2,4,6} };

    for (int i = 0; i < 8; i++)
    {
        if (chess[mask[i][0]] == constX && chess[mask[i][1]] == constX && chess[mask[i][2]] == constX)
            return 1;
        else if (chess[mask[i][0]] == constO && chess[mask[i][1]] == constO && chess[mask[i][2]] == constO)
            return -1;
    }

    return 0;
}

//return the number of zeros in chess[]
int GetZero(const int chess[9])
{
    int zeros = 0;
    for (int i = 0; i < 9; i++)
    {
        if (chess[i] == 0)
        {
            zeros++;
        }
    }
    return zeros;
}

//Get the utility of the node.(core of minmax)
int GetScore(const int chess[9], int maxmin)
{
    //maxmin == 1, max; maxmin == -1, min.
    int temp[9] = { 0 };
    for (int i = 0; i < 9; i++)
    {
        temp[i] = chess[i];
    }

    int go = 0;
    int remember = 0;
    if (maxmin == 1)
    {
        go = 1;
        remember = -2;
        for (int i = 0; i < 9; i++)
        {
            if (temp[i] == 0)
            {
                temp[i] = go;
                int iswin = IsWin(temp);
                if (iswin != 0 || (iswin==0 && GetZero(temp)==0))
                {
                    remember = iswin > remember ? iswin : remember;
                }
                else
                {
                    int tempscore = GetScore(temp, -maxmin);
                    remember = tempscore>remember ? tempscore : remember;
                }
                temp[i] = 0;
            }
        }
    }

    if (maxmin == -1)
    {
        go = 2;
        remember = 2;
        for (int i = 0; i < 9; i++)
        {
            if (temp[i] == 0)
            {
                temp[i] = go;
                int iswin = IsWin(temp);
                if (iswin != 0 || (iswin == 0 && GetZero(temp) == 0))
                {
                    remember = iswin < remember ? iswin : remember;
                }
                else
                {
                    int tempscore = GetScore(temp, -maxmin);
                    remember = tempscore<remember?tempscore:remember;
                }
                temp[i] = 0;
            }
        }
    }

    return remember;
}

//Get the next position to put X/O in
int GetNext(const int chess[9], int maxmin)
{
    //maxmin == 1, max; maxmin == -1, min.
    int temp[9] = { 0 };
    for (int i = 0; i < 9; i++)
    {
        temp[i] = chess[i];
    }

    int next = -1;

    int remember = 0;

    if (maxmin == 1)
    {
        remember = -2;
        for (int i = 0; i < 9; i++)
        {
            if (temp[i] == 0)
            {
                temp[i] = 1;
                int score = GetScore(temp, -maxmin);
                next = (score > remember) ? i : next;
                remember = (score > remember) ? score : remember;
                temp[i] = 0;
            }
        }
    }

    if (maxmin == -1)
    {
        remember = 2;
        for (int i = 0; i < 9; i++)
        {
            if (temp[i] == 0)
            {
                temp[i] = 2;
                int score = GetScore(temp, -maxmin);
                next = (score < remember) ? i : next;
                remember = (score < remember) ? score : remember;
                temp[i] = 0;
            }
        }
    }

    return next;
}

int GetFinalScore(const int chess[9])
{
    int finalscore = 0;
    int temp[9] = { 0 };
    for (int i = 0; i < 9; i++)
    {
        temp[i] = chess[i];
    }

    int maxmin = 1;
    while (IsWin(temp) == 0 && GetZero(temp) != 0)
    {
        temp[GetNext(temp, maxmin)] = maxmin == 1 ? 1 : 2;
        maxmin = -maxmin;
    }

    if (IsWin(temp) == 1)
    {
        finalscore = GetZero(temp) + 1;
    }
    if (IsWin(temp) == -1)
    {
        finalscore = - GetZero(temp) - 1;
    }
    if (IsWin(temp) == 0)
    {
        finalscore = 0;
    }

    return finalscore;
}

int main()
{
    int T;
//  cin >> T;
    T = 1;
    for (int k = 0; k < T; k++)
    {
        int chess[9] = { 0 };
        for (int i = 0; i < 3; i++)
            cin >> chess[i * 3 + 0] >> chess[i * 3 + 1] >> chess[i * 3 + 2];

        int score = GetFinalScore(chess);
        cout << score;
    }

    return 0;
}

阅读更多
想对作者说点什么?

博主推荐

换一批

没有更多推荐了,返回首页