C++编写一个“人机对弈“的下棋程序,四个棋子连成一线即为赢。人走棋的合法输入为0-6。棋盘是垂直放置,棋子落到底部

本文介绍了一个使用C++编写的四子棋程序,实现了人机对弈,玩家先手,计算机后手,通过判断合法走法、游戏结束条件以及计算最佳策略来决定胜负。
摘要由CSDN通过智能技术生成

题目:编写一个"人机对弈"的下棋程序,四个棋子连成一线即为赢。人走棋的合法输入为0-6。棋盘是垂直放置,棋子落到底部。

说明:这个程序可以选择是计算机先走还是人先走,我们的作业不要求这样,固定为人先走,计算机后走即可

程序结构可以参考如下结构,也可以按自己思路。

class game//这是个抽象类,抽象的是所有人走一步,计算机走一步的对弈游戏
    {
    public:
  enum who { HUMAN, NEUTRAL, COMPUTER }; 
 
  game( ) { move_number = 0; }
  virtual ~game( ) { }
  who play( );   //人先走,计算机后走,返回值是游戏的赢者,后面给出了此函数的定义
    protected:
        //以下虚函数可以被覆盖,也可以不被覆盖
  virtual void display_message(const string& message)const;//在屏幕显示信息message
             virtual int get_user_move( )const;       // 输出"Your move,please:",然后接受用户输入,并将输入返回
  virtual who last_mover( ) const 
   { return (move_number % 2 == 1 ? HUMAN : COMPUTER); }
  virtual int moves_completed( ) const { return move_number; }
  virtual who next_mover( ) const
   { return (move_number % 2 == 0 ? HUMAN : COMPUTER); }
  
        // 以下虚函数必须被覆盖
     virtual void make_move(const int& move)//将棋子真正下到棋盘上,此函数被子类覆盖
       { ++move_number; }
     virtual void restart( ) { move_number = 0; }//开始新的棋局

        //以下为纯虚函数 
        virtual who winning( )const =0;        //返回胜利者 
     virtual void display_status( )  = 0;   //显示游戏棋盘的当前状态
     virtual bool is_game_over( )  = 0;     //如果游戏结束,返回真
    virtual bool is_legal(const int& move)  = 0;   //如果给定走法为合法,就返回真
        virtual void make_computer_move( )=0;    //计算计算机所有的可能的走法,选出一种最好的,并调用make_move(best_move)
      
 private:
  int move_number; //当前已走的步数
  void make_human_move( );   //调用 get_user_move( ),并用is_legal(move)判断是否合法输入,若是则调用make_move(move)
    };

class c4 : public game//这个类是我们具体要实现的“四子棋”
    {
    public:
     c4( ) {restart( );}
    protected:
  
                virtual void make_move(const int& move); // 修改data[][],many_used[]和most_recent_column的值,并调用game::make_move(move)
  virtual void restart( );    //将data[6][7]各元素置为NEUTRAL,将many_used[7]各元素置为0 ,再调用game::restart();
         virtual game::who winning( )const ;
         virtual void display_status( ) ;  //显示棋盘的状态
  virtual bool is_game_over( ) ;
  virtual bool is_legal(const int& move) ; 
  virtual void make_computer_move( );       
    private:       
  who data[6][7];   //6行7列,表示棋盘
  int many_used[7]; //表示各列中已有多少个棋子
  int most_recent_column;  //最近下的棋子在哪列
    };

//人先走,计算机后走,返回值是游戏的赢者
game::who game::play()
{
 restart();
 
 while(!is_game_over())
 {
  display_status(); 
 
  if(last_mover()==COMPUTER)
   make_human_move();
  else
   make_computer_move();
 }
 display_status();
 return winning();
}
        
void main()
{
 c4 instance;
 game::who winner;
 winner=instance.play();
 switch(winner)
 {
  case c4::HUMAN: cout<<"You win!"<<endl;break;
  case c4::COMPUTER: cout<<"I win!"<<endl;break;
  case c4::NEUTRAL: cout<<"A draw"<<endl;break;
 }
}
 

 

 

实现代码:

#include<iostream>
#include<ctime>
using namespace std;
class game
{
    public:
		 int move_number; 
  enum who { HUMAN, NEUTRAL, COMPUTER}; 
  game( ) { move_number = 0; }
  virtual ~game( ) { };
  who play( );   
    protected:
  virtual int get_user_move( )const;     
  virtual who last_mover( ) const 
  { return (move_number % 2 == 1 ? HUMAN : COMPUTER); }
  virtual int moves_completed( ) const { return move_number; }
  virtual who next_mover( ) const
   { return (move_number % 2 == 0 ? HUMAN : COMPUTER); }
  virtual void make_move(const int& move)
       { ++move_number; }
  virtual void restart( ) { move_number = 0; }
        virtual who winning( )const =0;         
     virtual void display_status( )  = 0;   
     virtual bool is_game_over( )  = 0;    
    virtual bool is_legal(const int& move)  = 0;   
        virtual void make_computer_move( )=0;    
 private:
  void make_human_move( );  
    };
int game::get_user_move()const
{  int step;
	cout<<"Your move,please:";
	cin>>step;
	return step;
}
void game::make_human_move()
{   int step;
	step=get_user_move();
	if(is_legal(step))
	make_move(step);
	else
	{cout<<"The move is illegal!"<<endl;
      make_human_move();
	}
}
class c4 : public game
    {
    public:
     c4( ) {restart( );}
    protected:
  virtual void make_move(const int& move); 
  virtual void restart( );   
  virtual game::who winning( )const ;
  virtual void display_status( ) ; 
  virtual bool is_game_over( ) ;
  virtual bool is_legal(const int& move) ; 
  virtual void make_computer_move( );      
  bool if_two();
  bool if_three();
    private:       
  who data[6][7];   
  int many_used[7]; 
  int most_recent_column;  
    };
bool c4::is_game_over()
{int i,j;
	if(move_number==42) return true;
	for(i=0;i<6;++i)
	{
		for(j=0;j<4;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i][j+1]&&data[i][j]==data[i][j+2]&&data[i][j]==data[i][j+3])
				return true;
		}
	}
    for(i=0;i<3;++i)
	{
		for(j=0;j<7;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j]&&data[i][j]==data[i+2][j]&&data[i][j]==data[i+3][j])
				return true;
		}
	}
	for(i=0;i<3;++i)
	{
		for(j=0;j<4;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j+1]&&data[i][j]==data[i+2][j+2]&&data[i][j]==data[i+3][j+3])
				return true;
		}
	}
	for(i=0;i<3;++i)
    {
        for(j=6;j>2;--j)
		{
        if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j-1]&&data[i][j]==data[i+2][j-2]&&data[i][j]==data[i+3][j-3])
        return true;
		}
    }
	return false;

}
bool c4::if_two()
{
	int i,j;
	for(i=0;i<6;++i)
	{
		for(j=0;j<6;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i][j+1])
				return true;
		}
	}
	for(i=0;i<5;++i)
	{
		for(j=0;j<7;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j])
				return true;
		}
	}
	for(i=0;i<5;++i)
	{
		for(j=0;j<6;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j+1])
				return true;
		}
	}
	for(i=0;i<5;++i)
	{
		for(j=6;j>0;--j)
		{
             if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j-1])
				return true;
		}
	}
	return false;
}
bool c4::if_three()
{
	int i,j;
	for(i=0;i<6;++i)
	{
		for(j=0;j<5;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i][j+1]&&data[i][j]==data[i][j+2])
				return true;
		}
	}
	for(i=0;i<4;++i)
	{
		for(j=0;j<7;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j]&&data[i][j]==data[i+2][j])
				return true;
		}
	}
	for(i=0;i<4;++i)
	{
		for(j=0;j<5;++j)
		{
			if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j+1]&&data[i][j]==data[i+2][j+2])
				return true;
		}
	}
	for(i=0;i<4;++i)
	{
		for(j=6;j>0;--j)
		{
             if(data[i][j]!=NEUTRAL&&data[i][j]==data[i+1][j-1]&&data[i][j]==data[i+2][j-2])
				return true;
		}
	}
	return false;
}
bool c4::is_legal(const int& move)
{
	if(many_used[move]<6&&move>=0&&move<7)
		return true;
	else 
		return false;
}

game::who c4::winning()const
{
   if(move_number==6*7)
       return NEUTRAL;
    else
		return game::last_mover();
}
 
void c4::make_computer_move()
{
	if(move_number==1)
	{
		while(rand()>=6)
		{
		   most_recent_column=rand()%6;
		}
	    make_move(most_recent_column);
     	return ;
	}
     int i,mark;
    int move,score[7],max_score=0,best_move=0;
    for(i=0;i<7;i++)
	{
        score[i]=0;
	}
   for(move=0;move<7;move++)
    {
        if(many_used[move]<6)
        {
            data[5-many_used[move]][move]=COMPUTER;
            if(is_game_over()&&is_legal(move))
              {
               make_move(move);
               return ;
              }
             data[5-many_used[move]][move]=NEUTRAL;
        }
    }
  for(move=0;move<7;move++)
  {
      if(many_used[move]<6)
      {
        data[5-many_used[move]][move]=HUMAN;
        if(is_game_over()&&is_legal(move))
           {
             make_move(move);
             return ;
           }
          data[5-many_used[move]][move]=NEUTRAL;
      }
  }
    
      for(move=0;move<7;move++)
      {
          if(is_legal(move))
          {
              data[5-many_used[move]][move]=HUMAN;
              if(if_three())
              {
                  mark=5;
                 if(mark>score[move])
                     score[move]=mark;
              }
              data[5-many_used[move]][move]=NEUTRAL;
          }
          else
              continue;
      }
        for(move=0;move<7;move++)
        {
            if(is_legal(move))
            {
                data[5-many_used[move]][move]=COMPUTER;
                if(if_three())
                {
                    mark=4;
                    if(mark>score[move])
                    score[move]=mark;
                }
                data[5-many_used[move]][move]=NEUTRAL;
            }
            else
                continue;
        }
    for(move=0;move<7;move++)
    {
        if(is_legal(move))
        {
            data[5-many_used[move]][move]=HUMAN;
            if(if_two())
            {
                mark=3;
                if(mark>score[move])
                score[move]=mark;
            }
            data[5-many_used[move]][move]=NEUTRAL;
        }
        else
            continue;
    }
      for(move=0;move<7;move++)
      {
          if(is_legal(move))
          {
              data[5-many_used[move]][move]=COMPUTER;
              if(if_two())
              {
                mark=2;
                  if(mark>score[move])
                      score[move]=mark;
              }
              data[5-many_used[move]][move]=NEUTRAL;
          }
          else
              continue;
      }
    for(i=0;i<7;i++)
        if(max_score<=score[i])
        {
            best_move=i;
            max_score=score[i];
        }
    make_move(best_move);
}
void c4::make_move(const int& move)
{
	most_recent_column=move;
		 if(next_mover()==HUMAN)
		 {
        data[5-many_used[move]][move]=HUMAN;
		 }
         else
		 {
        data[5-many_used[move]][move]=COMPUTER;
		 }
    many_used[move]++;
	game::make_move(move);
}
void c4::display_status()
{
    int i,j;
    for(i=0;i<6;i++)
    {
        cout<<"          ";
        for(j=0;j<7;j++)
        {if(data[i][j]==HUMAN)
            cout<<"  "<<"*";
            else if(data[i][j]==COMPUTER)
             cout<<"  "<<"#";
            else
             cout<<"  "<<".";
        }
         cout<<endl;
    }
    cout<<"            ___________________"<<endl;
    cout<<"            0  1  2  3  4  5  6"<<endl;
    cout<<"                               Human:*   Computer:#"<<endl;
    cout<<"当前各列棋子数分别为:";
    for(i=0;i<7;i++)
        cout<<" "<<many_used[i];
    cout<<endl;
   cout<<"当前已经走的步数:"<<move_number<<endl;
}  
void c4::restart()
{
	int i,j;
	for(i=0;i<6;++i)
	{
		for(j=0;j<7;++j)
		{
			data[i][j]=NEUTRAL;
			many_used[j]=0;
		}
	}
	game::restart();
}
game::who game::play()
{
 restart();
 
 while(!is_game_over())
 {
  display_status(); 
 
  if(last_mover()==COMPUTER)
   make_human_move();
  else
   make_computer_move();
 }
 display_status();
 return winning();
}    
void main()
{
 srand((unsigned int)time(NULL));
 c4 instance;
 game::who winner;
 winner=instance.play();
 switch(winner)
 {
  case c4::HUMAN: cout<<"You win!"<<endl;break;
  case c4::COMPUTER: cout<<"Sorry,the computer win."<<endl;break;
  case c4::NEUTRAL: cout<<"A draw"<<endl;break;
 }
}

运行结果:

5b4f431e40b1410c86fca685ec3e4006.png

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值