人机下棋程序

2. 人机下棋: 3×3 棋盘上,计算机为一方,用户为一方,交替画
X ”和“ O ”,在行、列、对角线上谁先练成一条直线谁就获得
胜利。用类的思想完成,具体功能要求如下:
1 )状态显示:计算机可正确显示棋盘,给出提示信息和胜负判
断。
2 )用户选择:用户可以选择是先下还是后下,并选择棋子是
X ”还是“ O ”。
3 )每一步都用图形化方式顺序输出,例如
O * X
X X *
O * *
棋盘初始化为(“ * ”表示空格)
* * *
* * *
* * *
4 )棋盘大小设置:完成上述功能后考虑灵活设置棋盘大小。
5 注意:可以从积分规则和棋手的下棋策略出发考虑增强程序
的智能性
提示: 解题关键是解决计算机下棋时该下哪个位置,可以用量化的
思想解决该问题。假设计算机用“ X ”,用户用“ O ”,计算机下
棋时应考虑所有空位置,并按照行、列、对角线计算每个空位的分
值,在某行(列或对角线)上按以下规则进行计分:
若已有“ XX ”,计 50
若已有“ OO ”,计 25 分;
若已有“ X* ”,计 10 分;
若已有“ O* ”,计 8 分;
如已有“ ** ”,计 4
其中,“ * ”表示空格,也可用数字 1~9 表示空格。以上计分规则仅
供参考。
代码示例:
#include<iostream>

using namespace std;

class Game
{
private:
    int size;
    char computer;//机器的棋子
    char people;//人选择的棋子
    char board[100][100]={'*'};//棋盘

public:
    Game(int si):size(si){}

    void display()//输出棋盘
    {
        for(int i=0;i<size;i++)
        {
            for(int j=0;j<size;j++)
            {
                cout<<board[i][j];
            }
            cout<<endl;
        }
        cout<<endl;
    }

    int score(int row,int col)//计算分数,用于辅助机器下棋
    {
        int scores=0;
        //计算该行的分数
        for(int i=0;i<size-1;i++)
        {
            if(board[row][i]=='X'&&board[row][i+1]=='X') scores+=50;
            else if(board[row][i]=='O'&&board[row][i+1]=='O') scores+=25;
            else if(board[row][i]=='X'&&board[row][i+1]=='*') scores+=10;
            else if(board[row][i]=='*'&&board[row][i+1]=='X') scores+=10;
            else if(board[row][i]=='O'&&board[row][i+1]=='*') scores+=8;
            else if(board[row][i]=='*'&&board[row][i+1]=='O') scores+=8;
            else if(board[row][i]=='*'&&board[row][i+1]=='*') scores+=4;
        }
        //计算该列的分数
        for(int i=0;i<size-1;i++)
        {
            if(board[i][col]=='X'&&board[i+1][col]=='X') scores+=50;
            else if(board[i][col]=='O'&&board[i+1][col]=='O') scores+=25;
            else if(board[i][col]=='X'&&board[i+1][col]=='*') scores+=10;
            else if(board[i][col]=='*'&&board[i+1][col]=='X') scores+=10;
            else if(board[i][col]=='O'&&board[i+1][col]=='*') scores+=8;
            else if(board[i][col]=='*'&&board[i+1][col]=='O') scores+=8;
            else if(board[i][col]=='*'&&board[i+1][col]=='*') scores+=4;
        }
        if(row==col) //计算向右斜的对角线
        {
            for(int i=0;i<size-1;i++)
        {
            if(board[i][i]=='X'&&board[i+1][i+1]=='X') scores+=50;
            else if(board[i][i]=='O'&&board[i+1][i+1]=='O') scores+=25;
            else if(board[i][i]=='X'&&board[i+1][i+1]=='*') scores+=10;
            else if(board[i][i]=='*'&&board[i+1][i+1]=='X') scores+=10;
            else if(board[i][i]=='O'&&board[i+1][i+1]=='*') scores+=8;
            else if(board[i][i]=='*'&&board[i+1][i+1]=='O') scores+=8;
            else if(board[i][i]=='*'&&board[i+1][i+1]=='*') scores+=4;
        }
        }
        if((row+col)==size-1)//计算向左斜的对角线
        {
            for(int i=0,j=size-1;i<size-1;i++,j--)
        {
            if(board[i][j]=='X'&&board[i+1][i+1]=='X') scores+=50;
            else if(board[i][j]=='O'&&board[i+1][j-1]=='O') scores+=25;
            else if(board[i][j]=='X'&&board[i+1][j-1]=='*') scores+=10;
            else if(board[i][j]=='*'&&board[i+1][j-1]=='X') scores+=10;
            else if(board[i][j]=='O'&&board[i+1][j-1]=='*') scores+=8;
            else if(board[i][j]=='*'&&board[i+1][j-1]=='O') scores+=8;
            else if(board[i][j]=='*'&&board[i+1][j-1]=='*') scores+=4;
        }
        }

        return scores;
    }

    void peopleplay(int row,int col)//人下
    {
        board[row][col]=people;
    }

    void computerplay()//机器下
    {
        int mscore=0,x,y;
        for(int i=0;i<size;i++)
        {
            for(int j=0;j<size;j++)
            {
                if(board[i][j]=='*')
                    if(score(i,j)>mscore)
                    {
                        mscore=score(i,j);
                        x=i;
                        y=j;
                    }
            }
        }
        board[x][y]=computer;
    }

    int finish()//判断是否比赛完成,以及谁赢了(1人赢了 2机器赢了 3平局 0比赛还没结束)
    {
        //检查行
        for(int i=0;i<size;i++)
        {
            char c=board[i][size-1];
            int count=0;
            for(int j=0;j<size-1;j++)
            {
                if(board[i][size-1]=='*') break;
                if(board[i][j]=='*') break;
                if(board[i][j]==c)
                {
                    count+=1;
                }
            }
            if(count==size-1)
            {
                if(c==people) return 1;
                else return 2;
            }
        }
        //检查列
        for(int j=0;j<size;j++)
        {
            char c=board[size-1][j];
            int count=0;
            for(int i=0;i<size-1;i++)
            {
                if(board[size-1][j]=='*') break;
                if(board[i][j]=='*') break;
                if(board[i][j]==c)
                {
                    count+=1;
                }
            }
            if(count==size-1)
            {
                if(c==people) return 1;
                else return 2;
            }
        }
        //检查向右斜的对角线
        int count=0;
        for(int i=1;i<size;i++)
        {
            char c=board[0][0];
            if(board[i][i]=='*') break;
            if(board[i][i]==c)
            {
                ++count;
            }
            if(count==size-1)
            {
                if(c==people) return 1;
                else return 2;
            }
        }
        //检查向左斜的对角线
        //该对角线上i+j=size-1
        count=0;
        for(int i=1;i<size;i++)
        {
            char c=board[0][size-1];
            if(board[i][size-1-i]=='*') break;
            if(board[i][size-1-i]==c)
            {
                ++count;
            }
            if(count==size-1)
            {
                if(c==people) return 1;
                else return 2;
            }
        }
        //检查是否平局
         count=0;
        for(int i=0;i<size;i++)
        {
            for(int j=0;j<size;j++)
            {
               // if(board[i][j]=='*') break;
               // else count++;
               if(board[i][j]!='*') ++count;
            }
            if(count==size*size) return 3;
        }


        return 0;
    }


    void play()
    {
        for(int i=0;i<size;i++)
            for(int j=0;j<size;j++)
                board[i][j]='*';
        cout<<"请选择1先下还是2后下:";
        int x;
        cin>>x;
        cout<<"请选择棋子:X/O:";
        cin>>people;
        computer=(people=='X')?'O':'X';
        if(x==1)
            {
                cout<<"请选择下棋位置(行 列):";
                int x,y;
                cin>>x>>y;
                peopleplay(x,y);//人下
                display();
            }
        do
        {
            computerplay();//机器下
            display();
            if(finish()==1)//判断是否比赛完成
            {
                cout<<"你赢了!"<<endl;
                break;
            }
            else if(finish()==2)
            {
                cout<<"机器赢了!"<<endl;
                break;
            }
            else if(finish()==3)
            {
                cout<<"平局!"<<endl;
                break;
            }
            cout<<"请选择下棋位置(行 列):";
            int x,y;
            cin>>x>>y;
            peopleplay(x,y);//人下
            display();
            if(finish()==1)//判断是否比赛完成
            {
                cout<<"你赢了!"<<endl;
                break;
            }
            else if(finish()==2)
            {
                cout<<"机器赢了!"<<endl;
                break;
            }
            else if(finish()==3)
            {
                cout<<"平局!"<<endl;
                break;
            }

        }while(1);

    }
};


int main()
{
    int s;
    cout<<"请输入棋盘大小:";
    cin>>s;
    Game game(s);
    game.play();
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值