写了好久的博客一直在草稿箱忘了发,到发下一篇才看到。qAq。
废话不说了上效果图。→_→
代码点开,control+F5,走!
输入开始游戏指令
干掉电脑了,不过瘾的话再来一把
接下来,是代码,将代码分为头文件game.h,游戏的核心文件game.c,和test.c
Game.c(我把它叫做游戏的核心文件)
初始化
使用memset函数将数组里的元素都初始化成‘空格’,注意添加string.h头文件
void Initboard(char Checkerboard[ROW ][COL ],int row,int col)
{
memset(Checkerboard,' ',row*col*sizeof(Checkerboard[0][0]));
}
打印棋盘
这里用到了制表符,可以使我们的棋盘看起来更加的精美
void Printboard(char Checkerboard[ROW][COL],int row,int col)
{
int i = 0 ;
int j = 0 ;
printf ("┏" );
for (j=0 ;j<col-1 ;j++)
{
printf ("━┳" );
}
printf ("━┓\n" );
for (i=0 ;i<row;i++)
{
printf ("┃" );
for (j=0 ;j<col;j++)
{
printf (" %c" ,Checkerboard[i][j]);
printf ("┃" );
}
printf ("\n" );
if (i<row-1 )
{
printf ("┣" );
for (j=0 ;j<col-1 ;j++)
{
printf ("━╋" );
}
printf ("━┫\n" );
}
}
printf ("┗" );
for (j=0 ;j<col-1 ;j++)
{
printf ("━┻" );
}
printf ("━┛\n" );
}
玩家下棋
首先玩家不是程序猿,他可不知道数组的下标是从0开始的,所以在‘下棋’的时候,我们要注意将玩家输入的坐标下标都进行-1的操作。而且要注意,这里的循环一定要用一个死循环,落棋再退出,因为玩家有无数种理由,无限输错。
void Playermove(char Checkerboard[ROW][COL],int row,int col)
{
int i = 0 ;
int j = 0 ;
while (1 )
{
printf ("请玩家输入坐标:" );
scanf ("%d%d" ,&i,&j);
if (i>=1 &&i<=row&&j>=1 &&j<=col)
{
if (Checkerboard[i-1 ][j-1 ]==' ' )
{
Checkerboard[i-1 ][j-1 ]='o' ;
break ;
}
else
{
printf ("对不起,该坐标被占用,请重新输\n" );
}
}
else
{
printf ("对不起,您的输入有误,请重新输\n" );
}
}
}
电脑下棋
这里要用到rand产生一个随机数,先加头文件stdlib.h,但是rand()函数产生的随机数好像一点也不随机,那我们在加一个srand((unsigned int)time(NULL))(我放在的test.c里)进去让他在随机一点,记得头文件time.h。
void Computermove(char Checkerboard[ROW][COL],int row,int col)
{
int i = 0 ;
int j = 0 ;
while (1 )
{
i=rand ()%row ;
j=rand ()%col ;
if (Checkerboard[i][j]==' ' )
{
Checkerboard[i][j]='x' ;
break ;
}
}
}
输赢判定
这里我把棋盘拆成了内块与外块,这样在判定时,不会访问到棋盘以外的地方,解决了越界的问题。
char Judge(char Checkerboard[ROW][COL],int row,int col)
{
int i = 0 ;
int j = 0 ;
for (i=1 ;i<row-1 ;i++)
{
for (j=1 ;j<col-1 ;j++)
{
if (Checkerboard[i][j]==Checkerboard[i][j+1 ]&&Checkerboard[i][j]==Checkerboard[i][j-1 ]&&Checkerboard[i][j]!=' ' )
{
return Checkerboard[i][j];
}
if (Checkerboard[i][j]==Checkerboard[i+1 ][j]&&Checkerboard[i][j]==Checkerboard[i-1 ][j]&&Checkerboard[i][j]!=' ' )
{
return Checkerboard[i][j];
}
if (Checkerboard[i][j]==Checkerboard[i+1 ][j+1 ]&&Checkerboard[i][j]==Checkerboard[i-1 ][j-1 ]&&Checkerboard[i][j]!=' ' )
{
return Checkerboard[i][j];
}
if (Checkerboard[i][j]==Checkerboard[i+1 ][j-1 ]&&Checkerboard[i][j]==Checkerboard[i-1 ][j+1 ]&&Checkerboard[i][j]!=' ' )
{
return Checkerboard[i][j];
}
}
}
for (i=1 ;i<row-1 ;i++)
{
if (Checkerboard[i][0 ]==Checkerboard[i+1 ][0 ]&&Checkerboard[i][0 ]==Checkerboard[i-1 ][0 ]&&Checkerboard[i][0 ]!=' ' )
{
return Checkerboard[i][0 ];
}
if (Checkerboard[i][col-1 ]==Checkerboard[i+1 ][col-1 ]&&Checkerboard[i][col-1 ]==Checkerboard[i-1 ][col-1 ]&&Checkerboard[i][col-1 ]!=' ' )
{
return Checkerboard[i][col-1 ];
}
}
for (j=1 ;j<col-1 ;j++)
{
if (Checkerboard[0 ][j]==Checkerboard[0 ][j+1 ]&&Checkerboard[0 ][j]==Checkerboard[0 ][j-1 ]&&Checkerboard[0 ][j]!=' ' )
{
return Checkerboard[0 ][j];
}
if (Checkerboard[row-1 ][j]==Checkerboard[row-1 ][j+1 ]&&Checkerboard[row-1 ][j]==Checkerboard[row-1 ][j-1 ]&&Checkerboard[row-1 ][j]!=' ' )
{
return Checkerboard[row-1 ][j];
}
}
if (Full(Checkerboard,ROW,COL))
{
return 'W' ;
}
return ' ' ;
}
这里有一个平局(流局)的函数,赶紧带上
static int Full(char Checkerboard[ROW][COL],int row,int col)
{
int i = 0 ;
int j = 0 ;
for (i=0 ;i<row;i++)
{
for (j=0 ;j<col;j++)
{
if (Checkerboard[i][j] == ' ' )
{
return 0 ;
}
}
}
return 1 ;
}
Test.c
这样一个简单的三子棋游戏核心的内容就完成了,然后我们进入test.c文件中,就可以直接调用之前写的文件。写完以后再用cls清一下屏幕,把多余的内容清理干净,玩家不会找不到自己玩到哪里了。
#define _CRT_SECURE_NO_WARNINGS 1
#include"game.h"
void menu()
{
printf ("■■■■■■三子棋游戏■■■■■■\n" );
printf ("■■■■■■■■■■■■■■■■■\n" );
printf ("■■■■■■■■■■■■■■■■■\n" );
printf ("■■■■■■1.开始游戏■■■■■■\n" );
printf ("■■■■■■■■■■■■■■■■■\n" );
printf ("■■■■■■0.退出游戏■■■■■■\n" );
printf ("■■■■■■■■■■■■■■■■■\n" );
}
void game()
{
char ret = 0 ;
char Checkerboard[ROW][COL] = {0 };
srand((unsigned int )time(NULL));
Initboard(Checkerboard,ROW,COL);
Printboard(Checkerboard,ROW,COL);
while (1 )
{
Playermove(Checkerboard,ROW,COL);
system("cls" );
ret=Judge(Checkerboard,ROW,COL);
if (ret!=' ' )
{
break ;
}
Computermove(Checkerboard,ROW,COL);
ret=Judge(Checkerboard,ROW,COL);
if (ret!=' ' )
{
break ;
}
Printboard(Checkerboard,ROW,COL);
}
if (ret=='o' )
{
printf ("恭喜您,击败电脑\n" );
Printboard(Checkerboard,ROW,COL);
}
else
{
if (ret=='x' )
{
printf ("很遗憾,您被电脑击败\n" );
Printboard(Checkerboard,ROW,COL);
}
else
{
if (ret=='W' )
{
printf ("很遗憾,您和电脑平局\n" );
Printboard(Checkerboard,ROW,COL);
}
}
}
}
void test()
{
int input = 0 ;
do
{
menu();
printf ("请输入指令:" );
scanf ("%d" ,&input);
switch (input)
{
case 0 :
printf ("即将退出游戏\n" );
Sleep(2000 );
system("cls" );
break ;
case 1 :
printf ("游戏即将开始\n" );
Sleep(2000 );
system("cls" );
game();
break ;
default :
printf ("输入错误,请您重新输入\n" );
break ;
}
}
while (input);
}
int main()
{
test();
return 0 ;
}
Game.h
头文件,这里定义了一个宏,row和col可以自行修改棋盘的大小,我这里演示用的5行5列的。注意test调用game的每一个函数都要写,不要偷懒TvT。
void InitBoard(char board[ROW ][COL ], int row, int col);
void PrintBoard(char board[ROW ][COL ], int row, int col);
void Playermove(char board[ROW ][COL ], int row, int col);
void Computermove(char board[ROW ][COL ], int row, int col);
char Judge(char board[ROW ][COL ], int row, int col);
int Full(char board[ROW ][COL ], int row, int col);
一个简单三子棋游戏就搞定了,这是新手练手的很好的选择,入门的小伙伴们,还不赶紧动手试一下?