c语言五子棋人机对战
声明:我是菜鸡
我发此文,纯属 闲的蛋疼 ,反正就是想写一个。
代码很简单,无图片,游戏全部功能画面显示全部由 printf 打印,不过游戏里有很多小bug,不过不影响正常游戏,有兴趣的自己改进,应该不怎么难。
注:本游戏win7可完美运行,win10的话,棋盘的打印会略有鬼畜(变形)。
win10完美运行方案:点击屏幕左下角"开始"界面,搜索框输入cmd,出现命令提示符的黑框框后,(或者直接用五子棋.exe运行时的框框也行)右键黑框框顶栏(exe或者 命令提示符 名字那一栏)。选择属性->勾选窗口下方"使用旧版控制台",重启exe程序即可。
win10界面处理方法
搜索框输入cmd,出现命令提示符的黑框框后,(或者直接用五子棋.exe运行时的框框也行)右键黑框框顶栏(exe或者 命令提示符 名字那一栏)。选择属性
游戏展示
通过WSAD控制上下左右,空格键落子(要用英语输入法)
虽然它是我写的,但是我不用心的话一般是下不过它(不排除我五子棋比较菜的因素,你们玩可以试试)
代码我放后面你们自己复制粘贴。
注:默认是开启禁手的模式(不知道禁手的可以去看百度或者看下面链接),可以在设置里关闭禁手。
关于禁手:https://baike.baidu.com/item/%E7%A6%81%E6%89%8B/214940?fr=aladdin
游戏中输入 * 可以进入设置
输入3进入设置(额,这个地方应该优化一下,有兴趣的自己改)
开启或关闭后直接回车就行(这应该也算有个小bug)。
其他你们自己摸索吧。
核心代码展示
先展示这个游戏的灵魂:机器人函数,(想直接看全部代码的请略过)
void robot() /*机器人落子*/
{
int i, j, a, b;
int max1[2]={0}, max2[2]={0};
srand(time(NULL));
if(countpieces == 0) //备用于先手时
{
Rx=rand()%N;
Ry=rand()%N;
return ;
}
else if(countpieces == 1) //前俩子随机下
{
a=rand()%8;
Rx =Cx + next[a][0];
Ry =Cy + next[a][1];
return ;
}
else if(countpieces == 2)
{
a=rand()%8;
Rx =Rx + next[a][0];
Ry =Ry + next[a][1];
return ;
}
else if(countpieces >= 3) //开始判断每个位置落子的优先级
{
for(i=0;i<N;i++)
{
for(j=0;j<N;j++)
{
if(pieces[i][j] == 0)
{
pieces[i][j] = 2;
pieces1[i][j]=check1( 2,i, j);
pieces[i][j] = 0;
if(pieces1[max1[0]][max1[1]]<pieces1[i][j])
{
max1[0]=i;
max1[1]=j;
}
pieces[i][j] = 1;
pieces2[i][j]=check1(1,i, j);
pieces[i][j] = 0;
if(pieces2[max2[0]][max2[1]]<pieces2[i][j])
{
max2[0]=i;
max2[1]=j;
}
}
}
}
if(pieces1[max1[0]][max1[1]]>=pieces2[max2[0]][max2[1]]) //最后的比较
{
Rx=2*max1[0];
Ry=max1[1];
}
else
{
Rx=2*max2[0];
Ry=max2[1];
}
}
return;
}
int check1(int wj,int x, int y) /*机器人判断局势*/
{
int count[8] = {0}, Yxj, maxc=-1, maxd=-1; /*count置初值*/
for (int k = 0; k < 8; k++)
{
int i = x, j = y;
i += next[k][0];
j += next[k][1];
Hjs[k]=3;
while (i >= 0 && i < N && j >= 0 && j < N && count[k] < 5)
{
if (pieces[i][j] == pieces[x][y]) /*判断是否有落子及是否为同一玩家*/
{
count[k]++;
}
else /*无落子或不是同一玩家,退出循环*/
{
Hjs[k]=pieces[i][j];
break;
}
i += next[k][0];
j += next[k][1];
}
}
for (int k = 0; k < 4; k++) //判断优先级
{
if(count[k] + count[k + 4]==4)
{
if(wj==Rt)
{
Yxj=9;
}
else
{
Yxj=8;
}
}
else if(count[k] + count[k + 4]==3&&Hjs[k]==0&&Hjs[k+4]==0)
{
if(wj==Rt)
{
Yxj=7;
}
else
{
Yxj=6;
}
}
else if(count[k] + count[k + 4]==2&&Hjs[k]==0&&Hjs[k+4]==0)
{
if(wj==Rt)
{
Yxj=5;
}
else
{
Yxj=4;
}
}
else if(count[k] + count[k + 4]==3&&(Hjs[k]==0||Hjs[k+4]==0))
{
Yxj=4;
}
else if(count[k] + count[k + 4]==1&&(Hjs[k]==0&&Hjs[k+4]==0))
{
if(wj==Rt)
{
Yxj=3;
}
else
{
Yxj=2;
}
}
else if(count[k] + count[k + 4]<=1&&(Hjs[k]==0||Hjs[k+4]==0))
{
Yxj=2;
}
else
{
Yxj=1;
}
if(Yxj>maxd)
{
maxc=maxd;
maxd=Yxj;
}
else if(Yxj>maxc)
{
maxc=Yxj;
}
}
return maxd*10+maxc;
}
全部代码
#include <stdio.h>
#include <math.h>
#include <conio.h>
#include <ctype.h>
#include <stdlib.h>
#include <string.h>
#include <windows.h>
#include<time.h>
#define N 15 /*棋盘大小*/
void Getrun(); /*下棋模块*/
void tie(); /*和棋界面*/
void Set_up(); /*游戏设置*/
int Forbidden(); /*判断禁手*/
void forbidden(); /*禁手设置*/
void win(char ab); /*win界面*/
int check(int x, int y); /*判断输赢*/
void gotoxy(int x, int y); /*实现光标跳跃*/
void print(int Cx, int Cy); /*打造棋盘*/
void find(int x, int y, int k); /*查找棋子*/
void Game_h(char input); /*悔棋函数*/
void pause(); /*菜单*/
void player(); /*玩家状态*/
void window(); /*打印设置界面*/
void xianhou(); /*设置先后手*/
void robot(); /*机器人下棋*/
int check1(int wj,int x, int y); /*判断局势*/
int Rt=2, Rx, Ry, Gs1=0, Gs2=0; /*机器人编号,下子坐标, 优先等级*/
int Hjs[8];
int Rota[2], Rotb[2];
int pieces1[N][N] = {0};
int pieces2[N][N] = {0};
int pieces[N][N] = {0}, Cx, Cy;
int next[8][2] = {{0, 1}, {-1, 1}, {-1, 0}, {-1, -1}, {0, -1}, {1, -1}, {1, 0}, {1, 1}};
int flag, count = 0, temp = 0, vis = 0, countpieces = 0, log_a = 1, log_b = 1, forbid = 1;
char bz[10] = {"color E0"}; /*默认背景、字体颜色*/
char log_AAccount[20] = {0}, log_BAccount[20] = {0};
struct Find{
int ans, ans1, ans2;
}f[10];
struct XY { /*记录每次下棋的位置*/
int x, y;
};
struct node { /*利用链表把下棋的位置串起来*/
struct XY data;
struct node *next, *last;
};
typedef struct noda Node, *LinkLista;
LinkLista heada;
typedef struct node LNode, *LinkList;
LinkList head, prun;
int main()
{
char ch;
system("title 简易五子棋 --争梵制作"); /*设置标题*/
system("mode con cols = 62 lines = 41"); /*设置窗口大小*/
system(bz); /*设置颜色*/
while (1)
{
char n;
system("CLS"); /*清屏*/
system(bz); /*更新背景字体颜色*/
Getrun();
}
return 0;
}
void Getrun()
{
char ch;
Cy = N / 2, Cx = (2 * N - 1) / 2; /*初始方标位置*/
int winner, input;
LinkList p, p1;
prun = p1 = head = (LinkList)malloc(sizeof(LNode)); /*申请一个内存空间*/
head -> last = head -> next = NULL; /*使链表的头和尾指向空*/
p1 -> data.x = Cx / 2;
p1 -> data.y = Cy;
countpieces = 0; /*计算落子数*/
flag = 1, vis = 0;
memset(pieces, 0, sizeof(pieces)); /*初始化下棋数组*/
while (countpieces < N * N)
{
H: system("CLS"); /*清屏*/
print(Cx, Cy); /*打造棋盘*/
if (temp) /*显示提示信息*/
{
printf("已有棋子,请重新下棋!");
temp = 0;
}
/* 机器人 */
if(flag == Rt)
{
robot();
Cx = Rx; Cy = Ry;
input = 0x4F;
}
else
{
while (input = getch(), input != '*' &&
(flag != 2 || input != 0xE0) && !(flag == 1 && (input == 0x77 || input == 0x73 ||
input == 0x61 || input == 0x64)) && !(flag == 1 && input == 0x20 || flag == 2 && input == 0x4F));
if (input == '*') /*如果为*,打开菜单*/
{
P: pause(); /*进入菜单*/
while (ch = getch(), !(ch <= '3' ));
switch(ch)
{
case '1': break; /*继续游戏*/
case '2': return ; /*如果是0则退出程序*/
case '3': Set_up(); goto P; /*进入设置界面*/
}
}
else
{
if (flag == 2 && input == 0xE0) /*如果按下的是方向键,会填充两次输入,第一次为0xE0表示按下的是控制键*/
{
input = getch(); /*获得第二次输入信息*/
switch(input) /*判断方向键方向并移动光标位置*/
{
case 0x4B : Cy--; break;
case 0x48 : Cx-=2; break;
case 0x4D : Cy++; break;
case 0x50 : Cx+=2; break;
}
}
else if (flag == 1 && (input == 0x77 || input == 0x73 || input == 0x61 || input == 0x64))
{
switch(input) /*判断字母键方向并移动光标位置*/
{
case 0x61 : Cy--; break;
case 0x77 : Cx-=2; break;
case 0x64 : Cy++; break;
case 0x73 : Cx+=2; break;
}
}
if(Cy < 0)
Cy = N - 1; /*如果光标位置越界则移动到对侧*/
if(Cx < 0)
Cx = 2 * N - 2;
if(Cy > N - 1)
Cy = 0;
if(Cx > 2 * N - 1)
Cx = 0;
}
}
if (flag == 1 && input == 0x20 || flag == 2 && input == 0x4F)//确定下子
{
if (pieces[Cx / 2][Cy] == 0) /*判断是否可以落子*/
{ /*可以落子*/
p1 = prun; /*更新下棋的顺序*/
pieces[Cx / 2][Cy] = flag;
countpieces++;
if (flag == 1) /*改变游戏状态*/
flag = 2;
else flag = 1;
p = (LinkList)malloc(sizeof(LNode)); /*存下每次下棋的位置*/
p -> data.x = Cx / 2;
p -> data.y = Cy;
p -> last = p1;
p -> next = NULL;
p1 -> next = p;
prun = p1 = p;
winner = check(Cx / 2, Cy); /*检查判断输赢和游戏是否继续*/
if (winner != 1 && flag == 2 && forbid && Forbidden())
winner = 2;
if (winner || countpieces == N * N)
vis = 1;
if (winner == 1) /*A赢了*/
{
system("CLS"); /*清屏*/
print(Cx, Cy); /*重画棋盘*/
win('A');
break;
}
else if (winner == 2) /*B赢了*/
{
system("CLS"); /*清屏*/
print(Cx, Cy); /*重画棋盘*/
if(Forbidden()==1)
{
printf("\t\t抱歉,你触发了禁手!!!\n");
}
win('B');
break;
}
}
else /*该位置已有棋子*/
{
temp = 1; /*标记一下*/
system("CLS"); /*清屏*/
print(Cx, Cy); /*重画棋盘*/
}
}
}
if (countpieces == N * N) /*和棋*/
tie(); /*打印和棋界面*/
while (ch = getch(), ch != '\r'); /*按回车继续*/
}
void print(int Cx, int Cy) /*打造棋盘*/
{
if (!Cx)
{
for (int j = -1; j < N; j++)
{
if (j == Cy - 1 && !Cx)
printf("┏");
else if (j == Cy && !Cx)
printf(" ┓");
else printf(" ");
}
}
printf("\n");
for (int i = 0; i < 2 * N - 1; i++)
{
if (!Cy && i == Cx - 1)
printf("┏");
else if (!Cy && i == Cx + 1)
printf("┗");
else printf(" ");
for (int j = 0; j < N; j++)
{
if (!i)
{
if (!j)
{
if (pieces[i / 2][j] == 0) /*如果为0,证明无子*/
printf("┏━");
else if (pieces[i / 2][j] == 1) /*先手棋*/
printf("●━");
else if (pieces[i / 2][j] == 2) /*后手棋*/
printf("○━");
}
else if (j == N - 1)
{
if (pieces[i / 2][j] == 0)
printf("┓");
else if (pieces[i / 2][j] == 1)
printf("●");
else if (pieces[i / 2][j] == 2)
printf("○");
}
else
{
if (pieces[i / 2][j] == 0)
printf("┯━");
else if (pieces[i / 2][j] == 1)
printf("●━");
else if (pieces[i / 2][j] == 2)
printf("○━");
}
}
else if (i == 2 * N - 2)
{
if (!j)
{
if (pieces[i / 2][j] == 0)
printf("┗━");
else if (pieces[i / 2][j] == 1)
printf("●━");
else if (pieces[i / 2][j] == 2)
printf("○━");
}
else if (j == N - 1)
{
if (pieces[i / 2][j] == 0)
printf("┛");
else if (pieces[i / 2][j] == 1)
printf("●");
else if (pieces[i / 2][j] == 2)
printf("○");
}
else
{
if (pieces[i / 2][j] == 0)
printf("┷━");
else if (pieces[i / 2][j] == 1)
printf("●━");
else if (pieces[i / 2][j] == 2)
printf("○━");
}
}
else
{
if (i % 2 == 1)
{
if (!j || j == N - 1)
{
if (j == Cy - 1 && i == Cx - 1)
printf("┃┏");
else if (j == Cy && i == Cx - 1)
printf("┃┓");
else if (j == Cy - 1 && i == Cx + 1)
printf("┃┗");
else if (j == Cy && i == Cx + 1)
printf("┃┛");
else printf("┃ ");
}
else if (j == Cy - 1 && i == Cx - 1)
printf( "│┏");
else if (j == Cy && i == Cx - 1)
printf("│┓");
else if (j == Cy - 1 && i == Cx + 1)
printf("│┗");
else if (j == Cy && i == Cx + 1)
printf("│┛");
else printf("│ ");
}
else
{
if (!j)
{
if (pieces[i / 2][j] == 0)
printf("┠─");
else if (pieces[i / 2][j] == 1)
printf("●─");
else if (pieces[i / 2][j] == 2)
printf("○─");
}
else if (j == N - 1)
{
if (pieces[i / 2][j] == 0)
printf("┨");
else if (pieces[i / 2][j] == 1)
printf("●");
else if (pieces[i / 2][j] == 2)
printf("○");
}
else
{
if (pieces[i / 2][j] == 0)
printf("┼─");
else if (pieces[i / 2][j] == 1)
printf("●─");
else if (pieces[i / 2][j] == 2)
printf("○─");
}
}
}
}
printf("\n");
}
if (Cx + 2 == 2 * N)
{
for (int j = -1; j < N; j++)
{
if (j == Cy - 1 && Cx + 2 == 2 * N)
printf("┗");
else if (j == Cy && Cx + 2 == 2 * N)
printf(" ┛");
else printf(" ");
}
}
printf("\n");
if (!vis)
player(); /*在棋盘的最下面打印下棋玩家*/
}
int check(int x, int y) /*判断输赢*/
{
int count[8] = {0}, jul1, jul2, maxc=-1, maxd=-1; /*count置初值*/
for (int k = 0; k < 8; k++)
{
int i = x, j = y;
i += next[k][0];
j += next[k][1];
while (i >= 0 && i < N && j >= 0 && j < N && count[k] < 5)
{
if (pieces[i][j] == pieces[x][y]) /*判断是否有落子及是否为同一玩家*/
{
count[k]++;
}
else /*无落子或不是同一玩家,退出循环*/
{
// Hjs[k]=pieces[i][j];
break;
}
i += next[k][0];
j += next[k][1];
}
}
for (int k = 0; k < 4; k++)
{
if (count[k] + count[k + 4] >= 4) /*判断能否组成五子*/
return pieces[x][y];
}
return 0; /*未形成五子连成一条线的状态,返回0*/
}
void find(int x, int y, int k) /*查找棋子*/
{
int i = x, j = y;
i += next[k][0]; /*向规定方向查找*/
j += next[k][1];
while (1)
{
if (i <= 0 || i >= N - 1 || j <= 0 || j >= N - 1)
return ; /*到边界退出*/
if (pieces[i][j] == pieces[x][y]) /*判断是否为同一棋子*/
f[k].ans++; /*棋子个数加一*/
else if (!pieces[i][j]) /*还未下棋*/
{
if (!f[k].ans1 && pieces[i + next[k][0]][j + next[k][1]] == pieces[x][y] && pieces[i - next[k][0]][j - next[k][1]] == pieces[x][y])
f[k].ans1++; /*两边不为该棋子,中间空格数加一*/
else
{
f[k].ans2++; /*两头空格数加一*/
if (pieces[i + next[k][0]][j + next[k][1]] == pieces[x][y])
return ;
}
}
else return ;
if (f[k].ans2 >= 2) /*两头空格数大于一退出*/
return ;
i += next[k][0]; /*继续走*/
j += next[k][1];
}
}
int Forbidden() /*判断三三禁手*/
{
for (int i = 0; i < N; i++)
for (int j = 0; j < N; j++) /*遍历整个棋盘*/
{
memset(f, 0, sizeof(f));
if (pieces[i][j] == 1) /*如果为黑棋,进入*/
{
for (int k = 0; k < 8; k++)
find(i, j, k); /*找出八个方向的棋子数空格数*/
for (int k = 0; k < 4; k++)
for (int u = 0; u < 4; u++)
if (u != k) /*判断两个列,行,斜行*/
if ((f[k].ans + f[k + 4].ans == 2 && (!(f[k].ans1 + f[k + 4].ans1) && f[k].ans2 + f[k + 4].ans2 >= 3
|| (f[k].ans1 + f[k + 4].ans1 == 1 && f[k].ans2 && f[k + 4].ans2)))
&& (f[u].ans + f[u + 4].ans == 2 && (!(f[u].ans1 + f[u + 4].ans1) && f[u].ans2 + f[u + 4].ans2 >= 3
|| f[u].ans1 + f[u + 4].ans1 == 1 && f[u].ans2 && f[u + 4].ans2)))
return 1;
}
}
return 0;
}
void Set_up() /*游戏设置界面*/
{
char c;
l: system("CLS"); /*清屏*/
printf("\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
printf(" * *游戏设置* * *\n");
printf(" * ****************************************************** *\n");
printf(" * * * *\n");
printf(" * * 1.*禁手设置*.1 * *\n");
printf(" * * * *\n");
printf(" * * 2.*背景字体设置*.2 * *\n");
printf(" * * * *\n");
printf(" * * 3.*返回*.3 * *\n");
printf(" * * * *\n");
printf(" * ****************************************************** *\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n ");
while (c = getch(), c != '1' && c != '2' && c != '3' && c != '*');
switch(c)
{
case '*': return ;
case '1': forbidden(); break;
case '2': window(); break;
case '3': return ; break;
}
goto l;
}
void forbidden() /*禁手开关*/
{
char c;
system("CLS"); /*清屏*/
printf("\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
if (forbid)
printf(" * *已开启禁手,请选择:* *\n");
else printf(" * *已关闭禁手,请选择:* *\n");
printf(" * **************************************************** *\n");
printf(" * ************ ╔════╗ ╔════╗ ************ *\n");
printf(" * ******** ║N.开启.N║ ║F.关闭.F║ ******** *\n");
printf(" * ************ ╚════╝ ╚════╝ ************ *\n");
printf(" * **************************************************** *\n");
printf(" * *返回* *\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n ");
while (c = getch(), c != 'N' && c != 'F' && c != 'n' && c != 'f' && c != '*');/*判断是否为以上字符*/
switch(c)
{
case '*': return ;
case 'n':
case 'N': forbid = 1; break;
case 'f':
case 'F': forbid = 0; break;
}
if (forbid)
printf("开启成功!");
else printf("关闭成功!");
while (c = getch(), c != '\r');
}
void window() /*打印设置界面*/
{
L: int ans = 0;
char b = 0, z = 0, c, ch, b_z[2]; /*初始化数据*/
system(bz); /*更新颜色*/
system("CLS"); /*清屏*/
printf("\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
printf(" * ****************************************************** *\n");
printf(" * * * *\n");
printf(" * * 0 = 黑色 8 = 灰色 * *\n");
printf(" * * * *\n");
printf(" * * 1 = 蓝色 9 = 淡蓝色 * *\n");
printf(" * * * *\n");
printf(" * * 2 = 绿色 A = 淡绿色 * *\n");
printf(" * * * *\n");
printf(" * * 3 = 湖蓝色 B = 淡浅绿色 * *\n");
printf(" * * * *\n");
printf(" * * 4 = 红色 C = 淡红色 * *\n");
printf(" * * * *\n");
printf(" * * 5 = 紫色 D = 淡紫色 * *\n");
printf(" * * * *\n");
printf(" * * 6 = 黄色 E = 淡黄色 * *\n");
printf(" * * * *\n");
printf(" * * 7 = 白色 F = 亮白色 * *\n");
printf(" * * ╔════╗ * *\n");
printf(" * * ║* 返回 *║ * *\n");
printf(" * * ╚════╝ * *\n");
printf(" * ****************************************************** *\n");
printf(" * * * *\n");
printf(" * * 请输入背景颜色对应的编码: * *\n");
printf(" * * * *\n");
printf(" * * 请输入字体颜色对应的编码: * *\n");
printf(" * * * *\n");
printf(" * ****************************************************** *\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
gotoxy(33, 24); /*使光标跳到指定位置*/
while (c = getch()) /*输入操作的字符*/
{
if (c == '*') /*返回上次界面*/
return ;
if (c == '\r' && ans > 0) /*跳到字体颜色输入*/
break;
if (!(c >= '0' && c <= '9' || c >= 'a' && c <= 'f' || c >= 'A' && c <= 'F')) /*不是上面合法字符*/
{
if (c == 8 && ans > 0) /*判断是否为删除键*/
{
ans--; /*删除*/
b = 0;
printf("\b \b"); /*覆盖*/
}
continue;
}
if (ans < 1) /*最多输入一个*/
{
printf("%c", c); /*打印输入字符*/
b = c;
ans++; /*个数加一*/
}
}
ans = 0; /*初始化个数*/
gotoxy(33, 26); /*使光标跳到指定位置*/
while (c = getch())
{
if (c == '*') /*返回上次界面*/
return ;
if (c == '\r' && ans > 0) /*输入结束*/
break;
if (fabs(b - c) == 0 || fabs(b - c) == 32 || !(c >= '0' && c <= '9' || c >= 'a' && c <= 'f' || c >= 'A' && c <= 'F'))
{ /*不满足上面字符*/
if (c == 8 && ans > 0) /*判断删除键*/
{
ans--; /*删除*/
z = 0;
printf("\b \b"); /*覆盖*/
}
continue;
}
if (ans < 1) /*最多输入一个*/
{
printf("%c", c); /*打印输入字符*/
z = c;
ans++; /*个数加一*/
}
}
gotoxy(0, 30); /*光标回位*/
sprintf(b_z, "color %c%c", b, z); /*构建颜色字串*/
system(b_z); /*输出输入颜色*/
printf(" ╔═════╗ ╔═════╗ \n");
printf(" ║+确定更改+║ ║-重新设置-║ \n");
printf(" ╚═════╝ ╚═════╝ \n");
printf(" ");
while (ch = getch(), ch != '+' && ch != '-' && ch != '*');
if (ch == '*') /*返回界面*/
return ;
switch(ch) /*判断是否更改*/
{
case '+': strcpy(bz, b_z); break;
case '-': system("CLS"); goto L;
}
}
void player() /*打印下棋状态提示*/
{
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
printf(" * **************************************************** *\n");
printf(" * *************** *************** *\n");
if (flag == 1)
printf(" * *********** *请玩家●按空格键下棋!* *********** *\n");
else printf(" * *********** *请等待电脑○下棋!* *********** *\n");
printf(" * *************** *************** *\n");
printf(" * **************************************************** *\n");
printf(" * *调节* *\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n ");
}
void win(char ab) /*打印胜利界面*/
{
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
printf(" * *游戏结束* *\n");
printf(" * **************************************************** *\n");
printf(" * *************** *************** *\n");
if (ab == 'A')
printf(" * *********** *恭喜玩家你●赢了!* *********** *\n");
else printf(" * *********** *抱歉 电脑 ○赢了!* *********** *\n");
printf(" * *************** *************** *\n");
printf(" * **************************************************** *\n");
printf(" * *请按回车返回* *\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n ");
}
void tie() /*打印和棋界面*/
{
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
printf(" * *游戏结束* *\n");
printf(" * **************************************************** *\n");
printf(" * *************** *************** *\n");
printf(" * *********** *和棋* *********** *\n");
printf(" * *************** *************** *\n");
printf(" * **************************************************** *\n");
printf(" * *请按回车返回* *\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n ");
}
void Game_h(char input) /*悔棋、复棋*/
{
if (input == '-' && prun -> last != NULL)
{
pieces[prun -> data.x][prun -> data.y] = 0; /*使该位置无子*/
flag++;
flag = 2 - flag % 2; /*改变下棋状态*/
countpieces--; /*棋子数减一*/
prun = prun -> last; /*回到上次落棋点*/
Cx = prun -> data.x * 2;
Cy = prun -> data.y;
}
else if (input == '+' && prun -> next != NULL)
{
prun = prun -> next; /*恢复棋盘*/
Cx = prun -> data.x * 2; /*更新方标位置*/
Cy = prun -> data.y;
pieces[prun -> data.x][prun -> data.y] = flag;
flag++; /*更新下棋状态*/
flag = 2 - flag % 2;
countpieces++; /*棋子数加一*/
}
}
void pause() /*打印菜单界面*/
{
system("CLS"); /*清屏*/
printf("\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
printf(" * *菜 单* * *\n");
printf(" * ****************************************************** *\n");
printf(" * * * *\n");
printf(" * * 1.*继续游戏*.1 * *\n");
printf(" * * * *\n");
printf(" * * 2.*新游戏*.2 * *\n");
printf(" * * * *\n");
printf(" * * 3.*游戏设置*.3 * *\n");
printf(" * * * *\n");
printf(" * ****************************************************** *\n");
printf(" * * * * * * * * * * * * * * ** * * * * * * * * * * * * * *\n");
printf(" ");
}
void gotoxy(int x, int y) /*将光标移动到坐标为(x,y)的地方*/
{
CONSOLE_SCREEN_BUFFER_INFO csbiInfo;
HANDLE hConsoleOut;
hConsoleOut = GetStdHandle(STD_OUTPUT_HANDLE);
GetConsoleScreenBufferInfo(hConsoleOut,&csbiInfo);
csbiInfo.dwCursorPosition.X = x;
csbiInfo.dwCursorPosition.Y = y;
SetConsoleCursorPosition(hConsoleOut,csbiInfo.dwCursorPosition);
}
void robot() /*机器人落子*/
{
int i, j, a, b;
int max1[2]={0}, max2[2]={0};
srand(time(NULL));
if(countpieces == 0) //备用于先手时
{
Rx=rand()%N;
Ry=rand()%N;
return ;
}
else if(countpieces == 1) //前俩子随机下
{
a=rand()%8;
Rx =Cx + next[a][0];
Ry =Cy + next[a][1];
return ;
}
else if(countpieces == 2)
{
a=rand()%8;
Rx =Rx + next[a][0];
Ry =Ry + next[a][1];
return ;
}
else if(countpieces >= 3) //开始判断每个位置落子的优先级
{
for(i=0;i<N;i++)
{
for(j=0;j<N;j++)
{
if(pieces[i][j] == 0)
{
pieces[i][j] = 2;
pieces1[i][j]=check1( 2,i, j);
pieces[i][j] = 0;
if(pieces1[max1[0]][max1[1]]<pieces1[i][j])
{
max1[0]=i;
max1[1]=j;
}
pieces[i][j] = 1;
pieces2[i][j]=check1(1,i, j);
pieces[i][j] = 0;
if(pieces2[max2[0]][max2[1]]<pieces2[i][j])
{
max2[0]=i;
max2[1]=j;
}
}
}
}
if(pieces1[max1[0]][max1[1]]>=pieces2[max2[0]][max2[1]]) //最后的比较
{
Rx=2*max1[0];
Ry=max1[1];
}
else
{
Rx=2*max2[0];
Ry=max2[1];
}
}
return;
}
int check1(int wj,int x, int y) /*机器人判断局势*/
{
int count[8] = {0}, Yxj, maxc=-1, maxd=-1; /*count置初值*/
for (int k = 0; k < 8; k++)
{
int i = x, j = y;
i += next[k][0];
j += next[k][1];
Hjs[k]=3;
while (i >= 0 && i < N && j >= 0 && j < N && count[k] < 5)
{
if (pieces[i][j] == pieces[x][y]) /*判断是否有落子及是否为同一玩家*/
{
count[k]++;
}
else /*无落子或不是同一玩家,退出循环*/
{
Hjs[k]=pieces[i][j];
break;
}
i += next[k][0];
j += next[k][1];
}
}
for (int k = 0; k < 4; k++) //判断优先级
{
if(count[k] + count[k + 4]==4)
{
if(wj==Rt)
{
Yxj=9;
}
else
{
Yxj=8;
}
}
else if(count[k] + count[k + 4]==3&&Hjs[k]==0&&Hjs[k+4]==0)
{
if(wj==Rt)
{
Yxj=7;
}
else
{
Yxj=6;
}
}
else if(count[k] + count[k + 4]==2&&Hjs[k]==0&&Hjs[k+4]==0)
{
if(wj==Rt)
{
Yxj=5;
}
else
{
Yxj=4;
}
}
else if(count[k] + count[k + 4]==3&&(Hjs[k]==0||Hjs[k+4]==0))
{
Yxj=4;
}
else if(count[k] + count[k + 4]==1&&(Hjs[k]==0&&Hjs[k+4]==0))
{
if(wj==Rt)
{
Yxj=3;
}
else
{
Yxj=2;
}
}
else if(count[k] + count[k + 4]<=1&&(Hjs[k]==0||Hjs[k+4]==0))
{
Yxj=2;
}
else
{
Yxj=1;
}
if(Yxj>maxd)
{
maxc=maxd;
maxd=Yxj;
}
else if(Yxj>maxc)
{
maxc=Yxj;
}
}
return maxd*10+maxc;
}