五子棋智能算法解析(VC .net)

来源:互联网 发布:淘宝运营协议书 编辑:程序博客网 时间:2024/05/16 09:34

           大二的时候一次小学期作业写的五子棋智能算法。这里分析一下算法实现。

数据结构分析:

我们把整个棋盘看成一个二维数组,为了便于扩展,棋盘大小最大是25×25,可以自由选择棋盘大小。在棋盘的数组上,用数值的大小表示棋盘的危急程度,当然对于下棋双方来说,相对一边越而对另一边就越有利。

一个位置用一个结构来表示:

struct Seat

{

       int x;//x坐标

       int y;//y坐标

       int Urgent;

};

这个结构包含棋盘上的坐标位置和这个位置的危急程度。

整个棋盘上,还用到一个叫做“获胜组合”的结构,即每并排的五个子组成一个可能获胜组合,我们用一个结构来表示一个可能获胜组合:

       //获胜组合节点,一个节点为一种可能获胜组合

struct WinUnion{

       WinUnion(){}

       int Type;//标识组合方向--纵向:1;横向:2;反正斜:3;正斜:4

       bool HasDanger;//该组合数是否有效

       Seat seat[5];//五个组成一组

};//所有获胜组合数

       //每个位置上的可能获胜组合总数

在这个结构中Type表示组合的方向,由于有四个可能方向它们是:横向;反正斜;正斜,分别用1234来表示。这样只要下了子的位置,这个位置的危急程度就为0,因为没有人可以通过往这个地方下子可以取胜。

最后把下棋的角色封装成一个类,用于保存下棋过程中角色的棋盘情况,定义如下:

 

class PlayerStr

{

public:

       PlayerStr(){}

      

public:

       //标识是己方还是对方-1:对方;1:己方

       int flag;

       //标识是否手禁手约束

       bool Inhibiting;

       //桌面布子情况:-1:对方;1:己方

       int Table[25][25];

       //棋盘危急程度

       int Urgent[25][25];

       //每个位置指向所有相关联的可能获胜组合,动态创建可能获胜组合,并使相关联五个AllUnion指向它

       UnionNode AllUnion[25][25];

      

};

其中inhibiting表示是否禁手约束,先下子者为禁手,如果inhibitingtrue则使用禁手规则,否则不使用。Table数组表示桌面部子情况,0为没有子的情况,-1为对方的棋子,1为己方的棋子。Urgent数组为整个桌面的危急程度,这个危急程度跟Seat坐标的危急程度有分别,Seat坐标结构的危急程度指的是与这个坐标所组成的所有可能获胜组合对这个位置造成的危急程度,与这个位置组成的可能获胜组合中,越多对方的子在同一条直线上危急程度就越大。而Urgent数组则表示这个位置可能获胜组合越多就越危急。即Urgent数组是某个位置上所有可能获胜组合的可能获胜组合造成的危急总和。

AllUnion存储所有位置上的所有可能获胜组合链表组,从一个坐标查找链表可以找到所有与这个坐标组成的可能获胜组合。我们定义链表节点为:

struct UnionNode{

       WinUnion *UnionData;//指向一个组合

       UnionNode *Next;//下一个可能获胜组合

};

AllUnion存储了所有链表的链表头。

一个位置上的AllUnion[j+k][i]包含所有和这个位置相关的可能获胜组合WinUnion

例如AllUnion[0][0]可以通过Next访问到所有WinUnion组合的Seat值为:

 

 

Seat.x

Seat.y

一个WinUnion可能获胜组合

0

0

1

0

2

0

3

0

4

0

一个WinUnion可能获胜组合

0

0

0

1

0

2

0

3

0

4

一个WinUnion可能获胜组合

0

0

1

1

2

2

3

3

4

4

1 (0,0)位置的可能获胜组合左边

(int Urgent[25][25]UnionNode AllUnion[25][25]的关系:

AllUnion[25][25]的每个元素是一个链表,链表的每个元素记录一个可能获胜组合,所有元素都是五个位置的组合,组合都包含当前位置的坐标。一个位置下所有组合的Urgent;之和组成Urgent[25][25]Urgent[25][25]是从整个棋盘角度判断哪个位置更危急。)

关于获胜组合,补充一个图片,便于理解:

1 获胜组合

  

结构定义StructInfo.h

//--------------------------------智能五子棋数据结构--------------------------------

#include<stdio.h>

#include<stdlib.h>

#include<malloc.h>

#define ERROR 0

#define FALSE 0

#define TRUE  1

#define OVERFLOW 0

struct Seat

{

     int x;//x坐标

     int y;//y坐标

     int Urgent;

};

     //获胜组合节点,一个节点为一种可能获胜组合

struct WinUnion{

     WinUnion(){}

     int Type;//标识组合方向--纵向:;横向:;反正斜:;正斜:;

     bool HasDanger;//该组合数是否有效

     Seat seat[5];//五个组成一组

};//所有获胜组合数

     //每个位置上的可能获胜组合总数

struct UnionNode{

     WinUnion *UnionData;//指向一个组合

     UnionNode *Next;//下一个可能获胜组合

};

//***************************************************************

//PlayerStr对弈者数据类,标记是否先手(先下子)、棋盘状况,

//危急程度、可能获胜组合、棋盘上的每一空位指向它的可能获胜组合

//***************************************************************

 

 

class PlayerStr

{

public:

     PlayerStr(){}

    

public:

     //标识是己方还是对方-:对方;:己方

     int flag;

     //标识是否手禁手约束

     bool Inhibiting;

     //桌面布子情况:-:对方;:己方

     int Table[25][25];

     //棋盘危急程度

     int Urgent[25][25];

     //所有可能获胜组合

     //每个位置指向所有相关联的可能获胜组合,动态创建可能获胜组合,并使相关联五个AllUnion指向它

     UnionNode AllUnion[25][25];

    

};

 

 

智能实现声明头文件Intelligent.h

//--------------------------------智能类声明-------------------------------------

#include"StructInfo.h"

class Intell

{

public:

     Intell(){}

     void SetRowCol(int Row,int Col)

     {

         row=Row;

         col=Col;

     }

     void SetXY(int X,int Y)

     {

         x=X;

         y=Y;

     }

     int GetRow()

     {

         return row;

     }

     int GetCol()

     {

         return col;

     }

     int GetX()

     {

         return x;

     }

     int GetY()

     {

         return y;

     }

     //初始化函数

     void Initial(PlayerStr *Player1,PlayerStr *Player2);

     //是否非法——禁手

     bool IsIllegal(int x,int y,PlayerStr Player);

     //增加赋值

     void AddUrgent(int x,int y,PlayerStr *Player);

     //减少赋值

     void MinusUrgent(int x,int y,PlayerStr *Player);

     //返回最危急的位置下标

     Seat NextStep(PlayerStr Player);

private:

     //长联

     bool OverLine(int x,int y,PlayerStr Player);

     //活三

     bool DoubleThree(int x,int y,PlayerStr Player);

     //活四

     bool Four(int x,int y,PlayerStr Player);

     //双四

     bool DoubleFour(int x,int y,PlayerStr Player);

private:

     int row,col;

     int x,y;

 

};

 

智能类定义:

//-----------------------------------智能类函数的实现-------------------------------

//-----------------------------------智能类函数的实现-------------------------------

 

#include"Intelligent.h"

//***************************************************************************

//初始化对象:row,行数;col列数。Player1Player2:待初始化对象

//***************************************************************************

 

void Intell::Initial(PlayerStr *Player1,PlayerStr *Player2)

{

     int i,j,k=0;

     UnionNode *pnode,*qnode;

     WinUnion *pwin1,*pwin2;

     //初始化标识

     Player1->flag=-1;

     Player2->flag=1;

     //初始化TableUrgent

     for(i=0;i<col;i++)

         for(j=0;j<row;j++)

         {

              Player1->Table[i][j]=0;

              Player1->Urgent[i][j]=0;

              Player1->AllUnion[i][j].UnionData=NULL;

              Player1->AllUnion[i][j].Next=NULL;

 

              Player2->Table[i][j]=0;

              Player2->Urgent[i][j]=0;

              Player2->AllUnion[i][j].UnionData=NULL;

              Player2->AllUnion[i][j].Next=NULL;

 

         }

         //组合初始化

         //初始化纵向组合

     for(i=0;i<col;i++)

         for(j=0,k=0;j<row-4;j++)

         {//一个组合

              pwin1=(WinUnion *)malloc(sizeof(WinUnion));

              pwin1->HasDanger=TRUE;

              pwin1->Type=1;

              pwin2=(WinUnion *)malloc(sizeof(WinUnion));

              pwin2->HasDanger=TRUE;

              pwin2->Type=1;

              for(k=0;k<5;k++)

              {//组合下标赋值

                   pwin1->seat[k].x=i;

                   pwin1->seat[k].y=j+k;

                   pwin1->seat[k].Urgent=0;

                   pwin2->seat[k].x=i;

                   pwin2->seat[k].y=j+k;

                   pwin2->seat[k].Urgent=0;

              }

            //节点赋值

              for(k=0;k<5;k++)

              {

                  pnode=(UnionNode *)malloc(sizeof(UnionNode));

                  pnode->UnionData=pwin1;pnode->Next=NULL;

                   qnode=&Player1->AllUnion[j+k][i];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                  pnode=(UnionNode *)malloc(sizeof(UnionNode));

                   pnode->UnionData=pwin2;pnode->Next=NULL;

                   qnode=&Player2->AllUnion[j+k][i];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

              }

         }

         //初始化横向组合

     for(i=0;i<row;i++)

         for(j=0,k=0;j<col-4;j++)

         {//一个组合

              pwin1=(WinUnion *)malloc(sizeof(WinUnion));

              pwin1->HasDanger=TRUE;

              pwin1->Type=2;

              pwin2=(WinUnion *)malloc(sizeof(WinUnion));

              pwin2->HasDanger=TRUE;

              pwin2->Type=2;

              for(k=0;k<5;k++)

              {

                   pwin1->seat[k].x=j+k;

                   pwin1->seat[k].y=i;

                   pwin1->seat[k].Urgent=0;

                   pwin2->seat[k].x=j+k;

                   pwin2->seat[k].y=i;

                   pwin2->seat[k].Urgent=0;

              }

              //节点赋值

              for(k=0;k<5;k++)

              {

                   pnode=(UnionNode *)malloc(sizeof(UnionNode));

                  pnode->UnionData=pwin1;pnode->Next=NULL;

                   qnode=&Player1->AllUnion[i][j+k];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                  pnode=(UnionNode *)malloc(sizeof(UnionNode));

                   pnode->UnionData=pwin2;pnode->Next=NULL;

                   qnode=&Player2->AllUnion[i][j+k];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

              }

         }

         //反正斜方向所有可能获胜组合

         for(i=4;i<col;i++)

              for(j=0;i-j>=4;j++)

              {//一个组合

                   //(左上部分)包涵中线

                   pwin1=(WinUnion *)malloc(sizeof(WinUnion));

                  pwin1->HasDanger=TRUE;

                   pwin1->Type=3;

                  //pwin1->Urgent=0;

                  pwin2=(WinUnion *)malloc(sizeof(WinUnion));

                  pwin2->HasDanger=TRUE;

                   pwin2->Type=3;

                  //pwin2->Urgent=0;

                   for(k=0;k<5;k++)

                   {

                       pwin1->seat[k].x=i-j-k;

                       pwin1->seat[k].y=j+k;

                       pwin1->seat[k].Urgent=0;

                       pwin2->seat[k].x=i-j-k;

                       pwin2->seat[k].y=j+k;

                       pwin2->seat[k].Urgent=0;

                   }

                   //节点赋值

                   for(k=0;k<5;k++)

                   {

                   pnode=(UnionNode *)malloc(sizeof(UnionNode));

                  pnode->UnionData=pwin1;pnode->Next=NULL;

                   qnode=&Player1->AllUnion[j+k][i-j-k];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                  pnode=(UnionNode *)malloc(sizeof(UnionNode));

                   pnode->UnionData=pwin2;pnode->Next=NULL;

                   qnode=&Player2->AllUnion[j+k][i-j-k];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                   }

              }

              //右下部分

         for(i=1;i<row-4;i++)

              for(j=0;i+j<col-4;j++)

              {//一个组合

                   pwin1=(WinUnion *)malloc(sizeof(WinUnion));

                  pwin1->HasDanger=TRUE;

                   pwin1->Type=3;

                  //pwin1->Urgent=0;

                  pwin2=(WinUnion *)malloc(sizeof(WinUnion));

                  pwin2->HasDanger=TRUE;

                   pwin2->Type=3;

                  //pwin2->Urgent=0;

                   for(k=0;k<5;k++)

                   {

                       pwin1->seat[k].x=col-j-k-1;

                       pwin1->seat[k].y=i+j+k;

                       pwin1->seat[k].Urgent=0;

                       pwin2->seat[k].x=col-j-k-1;

                       pwin2->seat[k].y=i+j+k;

                       pwin2->seat[k].Urgent=0;

                   }

                   //节点赋值

                   for(k=0;k<5;k++)

                   {

                   pnode=(UnionNode *)malloc(sizeof(UnionNode));

                  pnode->UnionData=pwin1;pnode->Next=NULL;

                   qnode=&Player1->AllUnion[i+j+k][col-j-k-1];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                  pnode=(UnionNode *)malloc(sizeof(UnionNode));

                   pnode->UnionData=pwin2;pnode->Next=NULL;

                   qnode=&Player2->AllUnion[i+j+k][col-j-k-1];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                   }

              }

              //正斜方向所有可能获胜组合

         for(i=0;i<col-4;i++)

              for(j=0;row-i-j>4;j++)

              {//一个组合

                   //(右上部分)包含对角线

                   pwin1=(WinUnion *)malloc(sizeof(WinUnion));

                  pwin1->HasDanger=TRUE;

                   pwin1->Type=4;

                  //pwin1->Urgent=0;

                  pwin2=(WinUnion *)malloc(sizeof(WinUnion));

                  pwin2->HasDanger=TRUE;

                   pwin2->Type=4;

                  //pwin2->Urgent=0;

                   for(k=0;k<5;k++)

                   {

                       pwin1->seat[k].x=i+j+k;

                       pwin1->seat[k].y=j+k;

                       pwin1->seat[k].Urgent=0;

                       pwin2->seat[k].x=i+j+k;

                       pwin2->seat[k].y=j+k;

                       pwin2->seat[k].Urgent=0;

                   }

                   //节点赋值

                   for(k=0;k<5;k++)

                   {

                   pnode=(UnionNode *)malloc(sizeof(UnionNode));

                  pnode->UnionData=pwin1;pnode->Next=NULL;

                   qnode=&Player1->AllUnion[j+k][i+j+k];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                  pnode=(UnionNode *)malloc(sizeof(UnionNode));

                   pnode->UnionData=pwin2;pnode->Next=NULL;

                   qnode=&Player2->AllUnion[j+k][i+j+k];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                   }

              }

              //左下部分

         for(i=1;i<row-4;i++)

              for(j=0;i+j<col-4;j++)

              {//一个组合

                   pwin1=(WinUnion *)malloc(sizeof(WinUnion));

                  pwin1->HasDanger=TRUE;

                   pwin1->Type=4;

                  //pwin1->Urgent=0;

                  pwin2=(WinUnion *)malloc(sizeof(WinUnion));

                  pwin2->HasDanger=TRUE;

                   pwin2->Type=4;

                  //pwin2->Urgent=0;

                   for(k=0;k<5;k++)

                   {

                       pwin1->seat[k].x=j+k;

                       pwin1->seat[k].y=i+j+k;

                       pwin1->seat[k].Urgent=0;

                       pwin2->seat[k].x=j+k;

                       pwin2->seat[k].y=i+j+k;

                       pwin2->seat[k].Urgent=0;

                   }

                   //节点赋值

                   for(k=0;k<5;k++)

                   {

                   pnode=(UnionNode *)malloc(sizeof(UnionNode));

                  pnode->UnionData=pwin1;pnode->Next=NULL;

                   qnode=&Player1->AllUnion[i+j+k][j+k];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                  pnode=(UnionNode *)malloc(sizeof(UnionNode));

                   pnode->UnionData=pwin2;pnode->Next=NULL;

                   qnode=&Player2->AllUnion[i+j+k][j+k];

                   while(qnode->Next!=NULL)qnode=qnode->Next;

                   qnode->Next=pnode;

                   }

              }

                  

}

//***********************************************************************************

//Player增加Urgent值,xy为落子的位置

//***********************************************************************************

 

void Intell::AddUrgent(int x,int y,PlayerStr *Player)

{

     int i,inCount;

     UnionNode *pnode;

     Seat *seat;

     pnode=&Player->AllUnion[y-1][x-1];

     while(pnode->Next!=NULL)

     {

         pnode=pnode->Next;

         if(pnode->UnionData->HasDanger==TRUE)

         {

              inCount=0;//计算每一个组合棋子个数

              seat=pnode->UnionData->seat;

              for(i=0;i<5;i++)

              {

                   if(Player->Table[seat->y][seat->x]!=0)

                       inCount++;

                   seat++;

              }

              //普通赋值

              if(inCount==1)

              {

                   seat=pnode->UnionData->seat;

                   for(i=0;i<5;i++)

                   {

                       if(Player->Table[seat->y][seat->x]==0)

                       {

                            Player->Urgent[seat->y][seat->x]+=1;

                            seat->Urgent+=1;

                       }

                       seat++;

                   }

              }

              //加强赋值

              if(inCount==2)

              {

                   seat=pnode->UnionData->seat;

                   for(i=0;i<5;i++)

                   {

                       if(Player->Table[seat->y][seat->x]==0)

                       {

                            Player->Urgent[seat->y][seat->x]+=5;

                            seat->Urgent+=5;

                       }

                       seat++;

                   }

              }

              //加强赋值

              if(inCount==3)

              {

                   seat=pnode->UnionData->seat;

                   for(i=0;i<5;i++)

                   {

                       if(Player->Table[seat->y][seat->x]==0)

                       {

                            Player->Urgent[seat->y][seat->x]+=20;

                            seat->Urgent+=20;

                       }

                       seat++;

                   }

              }

              //加强赋值

              if(inCount==4)

              {

                   seat=pnode->UnionData->seat;

                   for(i=0;i<5;i++)

                   {

                       if(Player->Table[seat->y][seat->x]==0)

                       {

                            Player->Urgent[seat->y][seat->x]+=80;

                            seat->Urgent+=80;

                       }

                       seat++;

                   }

              }

         }

     }

}

//***********************************************************************************

//Player减少Urgent值,xy为落子的位置

//***********************************************************************************

void Intell::MinusUrgent(int x,int y,PlayerStr *Player)

{

     int i;

     UnionNode *pnode;

     Seat *seat;

     pnode=&Player->AllUnion[y-1][x-1];

     while(pnode->Next!=NULL)

     {

         pnode=pnode->Next;

         pnode->UnionData->HasDanger=FALSE;

         seat=pnode->UnionData->seat;

         for(i=0;i<5;i++)

         {

              if(Player->Table[seat->y][seat->x]==0)

              {

                   Player->Urgent[seat->y][seat->x]-=seat->Urgent;

                   seat->Urgent=0;

              }

              seat++;

         }

     }

}

 

//***********************************************************************************

//判断是否长连,是则返回True否则返回False;x,y是将要下的子,

//flag=己方受禁手约束,flag=-1,对方受禁手约束

//***********************************************************************************

bool Intell::OverLine(int x,int y,PlayerStr Player)

{

     int inx,iny,top,left,right,bottom,Count=0;//

     top=x-4;left=y-4;right=x+4;bottom=y+4;

     //假设在xy下一子

     Player->Table[x][y]=Player->flag;

     while(top<0)top++;

     while(left<0)left++;

     while(right>=col)right--;

     while(bottom>=row)bottom--;

     //纵向判断

     for(inx=x,iny=top,Count=0;iny<=bottom;iny++)

     {

         if(Player->Table[inx][iny]!=Player->flag)

         {

              Count=0;

         }

         else

         {

              Count++;

         }

         if(Count==6)

              return TRUE;

     }

     //横向判断

     for(inx=left,iny=y,Count=0;inx<=right;inx++)

     {

         if(Player->Table[inx][iny]!=Player->flag)

         {

              Count=0;

         }

         else

         {

              Count++;

         }

         if(Count==6)

              return TRUE;

     }

     //正斜方向判断

     for(inx=left,iny=top,Count=0;iny<=bottom;inx++,iny++)

     {

         if(Player->Table[inx][iny]!=Player->flag)

         {

              Count=0;

         }

         else

         {

              Count++;

         }

         if(Count==6)

              return TRUE;

     }

     //反正斜方向判断

     for(inx=right,iny=top,Count=0;iny<=bottom;inx--,iny++)

     {

         if(Player->Table[inx][iny]!=Player->flag)

         {

              Count=0;

         }

         else

         {

              Count++;

         }

         if(Count==6)

              return TRUE;

     }

     return FALSE;

}

//***********************************************************************************

//判断是否活四,是则返回True否则返回False;x,y是将要下的子,

//flag=己方受禁手约束,flag=-1,对方受禁手约束

//***********************************************************************************

bool Intell::Four(int x,int y,PlayerStr Player)

{

     int inx,iny,top,left,right,bottom,Count=-1;//

     top=x-4;left=y-4;right=x+4;bottom=y+4;

     //假设在xy下一子

     Player->Table[x][y]=Player->flag;

     while(top<0)top++;

     while(left<0)left++;

     while(right>=col)right--;

     while(bottom>=row)bottom--;

     //纵向判断

     for(inx=x,iny=top,Count=0;iny<=bottom;iny++)

     {

         if(Player->Table[inx][iny]==0)

         {

              Count=0;

         }

         else

              if(Player->Table[inx][iny]!=Player->flag)

              {

                   Count=-1;

              }

              else

                   if(Count>=0)

                       Count++;

         if(Count==4&&Player->Table[inx][iny+1]==0)

              return TRUE;

         else

              if(Count==4&&Player->Table[inx][iny+1]!=Player->flag)

                   Count=-1;

     }

     //横向判断

     for(inx=left,iny=y,Count=0;inx<=right;inx++)

     {

         if(Player->Table[inx][iny]==0)

         {

              Count=0;

         }

         else

              if(Player->Table[inx][iny]!=Player->flag)

              {

                   Count=-1;

              }

              else

                   if(Count>=0)

                       Count++;

         if(Count==4&&Player->Table[inx+1][iny]==0)

              return TRUE;

         else

              if(Count==4&&Player->Table[inx+1][iny]!=Player->flag)

                   Count=-1;

     }

     //正斜方向判断

     for(inx=left,iny=top,Count=0;iny<=bottom;inx++,iny++)

     {

         if(Player->Table[inx][iny]==0)

         {

              Count=0;

         }

         else

              if(Player->Table[inx][iny]!=Player->flag)

              {

                   Count=-1;

              }

              else

                   if(Count>=0)

                       Count++;

         if(Count==4&&Player->Table[inx+1][iny+1]==0)

              return TRUE;

         else

              if(Count==4&&Player->Table[inx+1][iny+1]!=Player->flag)

                   Count=-1;

     }

     //反正斜方向判断

     for(inx=right,iny=top,Count=0;iny<=bottom;inx--,iny++)

     {

         if(Player->Table[inx][iny]==0)

         {

              Count=0;

         }

         else

              if(Player->Table[inx][iny]!=Player->flag)

              {

                   Count=-1;

              }

              else

                   if(Count>=0)

                       Count++;

         if(Count==4&&Player->Table[inx-1][iny+1]==0)

              return TRUE;

         else

              if(Count==4&&Player->Table[inx-1][iny+1]!=Player->flag)

                   Count=-1;

     }

     return FALSE;

}

 

//***********************************************************************************

//判断在xy落下一子是否形成双四禁手如果是则返回TRUE否则返回FALSE

//

//***********************************************************************************

bool Intell::DoubleFour(int x,int y,PlayerStr Player)

{

     int i,j,count,n;

     UnionNode *pnode,*pfour;

     Seat seat;

     pfour=NULL;

     //假设下子

     Player->Table[x][y]=Player->flag;

     pnode=&Player->AllUnion[x][y];

     while(pnode->Next!=NULL)

     {

         pnode=pnode->Next;

         if(pnode->UnionData->HasDanger==FALSE)

         {

              count=0;

              for(i=0;i<5;i++)

              {

                   if(Player->Table[pnode->UnionData->seat[i].x][pnode->UnionData->seat[i].y]==-Player->flag)

                   {count=0;break;}

                   if(Player->Table[pnode->UnionData->seat[i].x][pnode->UnionData->seat[i].y]==Player->flag)

                       count++;

              }

              if(count==4)

              {

                   if(pfour!=NULL)

                   {

                       n=0;

                       for(i=0;i<5;i++)

                       {

                            if(Player->Table[pfour->UnionData->seat[i].x][pfour->UnionData->seat[i].y]==0)

                                 continue;

                            for(j=0;j<5;j++)

                            {

                                 if(pfour->UnionData->seat[i].x==pnode->UnionData->seat[j].x&&

                                     pfour->UnionData->seat[i].y==pnode->UnionData->seat[j].y)

                                     n++;

                            }

                       }

                   }

                   if(n==4)

                       continue;

                   for(i=0;i<5;i++)

                   {

                       if(Player->Table[pnode->UnionData->seat[i].x][pnode->UnionData->seat[i].y]==0)

                       {

                            seat.x=pnode->UnionData->seat[i].x;

                            seat.y=pnode->UnionData->seat[i].y;

                            break;

                       }

                   }

                   if(!OverLine(seat.x,seat.y,Player))

                   {

                       if(pfour!=NULL)

                            return TRUE;

                       else

                            pfour=pnode;

                   }

              }

         }

     }

     return FALSE;

}

 

//***********************************************************************************

//判断在xy落下一子是否三三禁手,如是则返回TRUE否则返回FALSE

//***********************************************************************************

bool Intell::DoubleThree(int x,int y,PlayerStr Player)

{

     int i,j,count,n;

     UnionNode *pnode,*pfour;

     Seat seat;

     pfour=NULL;

     //假设下子

     Player->Table[x][y]=Player->flag;

     pnode=&Player->AllUnion[x][y];

     while(pnode->Next!=NULL)

     {

         pnode=pnode->Next;

         if(pnode->UnionData->HasDanger==FALSE&&(Player->Table[pnode->UnionData->seat[0].x][pnode->UnionData->seat[0].y]==0

              ||Player->Table[pnode->UnionData->seat[4].y]==0))

         {

              count=0;

              for(i=0;i<5;i++)

              {

                   if(Player->Table[pnode->UnionData->seat[i].x][pnode->UnionData->seat[i].y]==-Player->flag)

                   {count=0;break;}

                   if(Player->Table[pnode->UnionData->seat[i].x][pnode->UnionData->seat[i].y]==Player->flag)

                       count++;

              }

              if(count==3)

              {

                   if(pfour!=NULL)

                   {

                       n=0;

                       for(i=0;i<5;i++)

                       {

                            if(Player->Table[pfour->UnionData->seat[i].x][pfour->UnionData->seat[i].y]==0)

                                 continue;

                            for(j=0;j<5;j++)

                            {

                                 if(pfour->UnionData->seat[i].x==pnode->UnionData->seat[j].x&&

                                     pfour->UnionData->seat[i].y==pnode->UnionData->seat[j].y)

                                     n++;

                            }

                       }

                   }

                   if(n==3)

                       continue;

                   if(Player->Table[pnode->UnionData->seat[0].x][pnode->UnionData->seat[0].y]==0)

                   {

                       for(i=1;i<5;i++)

                       {

                            if(Player->Table[pnode->UnionData->seat[i].x][pnode->UnionData->seat[i].y]==0)

                            {

                                 seat.x=pnode->UnionData->seat[i].x;

                                seat.y=pnode->UnionData->seat[i].y;

                                break;

                            }

                       }

                   }

                   else

                   {

                        for(i=0;i<4;i++)

                       {

                            if(Player->Table[pnode->UnionData->seat[i].x][pnode->UnionData->seat[i].y]==0)

                            {

                                 seat.x=pnode->UnionData->seat[i].x;

                                seat.y=pnode->UnionData->seat[i].y;

                                break;

                            }

                       }

                   }

                   if(Four(seat.x,seat.y,Player))

                   {

                       if(pfour!=NULL)

                            return TRUE;

                       else

                            pfour=pnode;

                   }

              }

         }

     }

     return FALSE;

}

 

    

//***********************************************************************************

//判断如果在xy落下一子是否非法

//***********************************************************************************

bool Intell::IsIllegal(int x,int y,PlayerStr Player)

{

     if(OverLine(x,y,Player))return true;

     if(DoubleThree(x,y,Player))return true;

     if(DoubleFour(x,y,Player))return true;

     return false;

}

 

 人机对战和网络人与人对战实现源码:

http://download.csdn.net/user/zhyuanshan

 

运行结果截图:

 

 

 

 

原创粉丝点击