什么网站可以发布信息,建设新农村网站,中国建设银行网上银行官网,杭州市区网站制作单位文章目录 前言一、前期准备模块化设计 二、框架搭建三、游戏实现打印棋盘代码优化玩家下棋电脑下棋判断输赢 四、结束 前言 三子棋是一种民间传统游戏#xff0c;又叫九宫棋、圈圈叉叉棋、一条龙、井字棋等。游戏分为双方对战#xff0c;双方依次在9宫格棋盘上摆放棋子#… 文章目录 前言一、前期准备模块化设计 二、框架搭建三、游戏实现打印棋盘代码优化玩家下棋电脑下棋判断输赢 四、结束 前言 三子棋是一种民间传统游戏又叫九宫棋、圈圈叉叉棋、一条龙、井字棋等。游戏分为双方对战双方依次在9宫格棋盘上摆放棋子率先将自己的三个棋子走成一条线就视为胜利而对方就算输了但是三子棋在很多时候会出现和棋的局面。 本篇博客就来进行讲解这个三子棋小游戏跟着我来一起看把本文使用的编译器是VS2022
一、前期准备
模块化设计
在写三子棋的时候我们先要了解一下什么事模块化设计 模块化程序设计是指在进行程序设计时将一个大程序按照功能划分为若干小程序模块每个小程序模块完成一个确定的功能并在这些模块之间建立必要的联系通过模块的互相协作完成整个功能的程序设计方法 上面是百度百科的介绍可能有同学看不懂简单来说就是份文件写在我们写一些程序的时候就会遇到一个.c文件里写很多会显得杂乱可读性会变的非常差那么我们就要使用份文件来写代码这样就会变得条理清晰可读性强这样是一种良好的编程习惯那么怎么做呢接下来看~~
建立一个game.h头文件存储行列信息包含函数库对函数进行声明建立一个game.c文件实现游戏中的函数建立一个test.c文件实现函数主体逻辑在书写时可用此函数进行测试将game.c和test.c文件中包含#includegame.h 二、框架搭建
创建好文件后将game.c和test.c引入game.h头文件的包含和函数的声明就在这里面 游戏界面 game.h
这里定义一个三行三列并且初始化当想要变成n行m列的只需要改一下这里define定义的就行
//行
#define ROW 3
//列
#define COL 3
//初始化棋盘
void InitBoard(char board[ROW][COL],int row,int col);玩家输入选择switch处理对应逻辑输入值顺便还可以作为循环结束的条件。
test.c
#define _CRT_SECURE_NO_WARNINGS 1
#includegame.hvoid menu()
{printf(\n);printf(**************************\n);printf(***** 1.play ******\n);printf(***** 0.exit ******\n);printf(**************************\n);printf(\n);
}void game()
{printf(玩游戏\n);
}int main()
{int input 0;do{menu();printf(请选择:);scanf(%d, input);switch (input){case 1:game();break;case 0:printf(退出游戏\n);break;default:printf(选择错误请重新选择\n);break;}} while (input);return 0;
}game.h
在这里把需要引入的头文件写入
#pragma once
#includestdio.h可以看到游戏已经正常运行了但是里面的game函数还没有实现接下来就让我们继续往下看完成一部分功能就运行一下看看及时发现BUG越早发现越容易找到BUG
三、游戏实现 创建棋盘初始化棋盘 game.h
void InitBoard(char board[ROW][COL],int row,int col);test.c
void game()
{//创建棋盘char board[ROW][COL];//初始化棋盘InitBoard(board, ROW, COL);
}game.c
初始化棋盘将数组所有元素初始化为空格
void InitBoard(char board[ROW][COL], int row, int col)
{int i 0;int j 0;for (i 0; i row; i){for (j 0; j col; j){board[i][j] ;//初始化为空格}}
}打印棋盘
game.h 打印棋盘
void DisplayBoard(char board[ROW][COL], int row,int col);test.c
DisplayBoard(board, ROW, COL);game.c
void DisplayBoard(char board[ROW][COL], int row, int col)
{
int i 0;for (i 0; i row; i){printf( %c | %c | %c \n, board[i][0], board[i][1], board[i][2]);if (i row - 1)printf(---|---|---\n);}
}如果我们要修改棋盘大小行是循环出来的但是列就写死了
代码优化
首先打印空格 空格和|要打印row行col列这里要注意的是当col列为col-1时才打印也就是说打印了2列|打印---也是一样的同理
game.c
void DisplayBoard(char board[ROW][COL], int row, int col)
{int i 0;int j 0;for (i 0; i row; i){for (j 0; j col; j){printf( %c , board[i][j]);if (j col - 1)printf(|);}printf(\n);if (i row - 1){for (j 0; j col; j){printf(---);if (j col - 1)printf(|);}printf(\n);}}
}我们将ROW和COL修改成10也是可以打印的 玩家下棋
game.h
void PlayMove(char board[ROW][COL], int row, int col);test.c
//玩家下棋
while (1)
{PlayMove(board, ROW, COL);DisplayBoard(board, ROW, COL);
}玩家下棋是不是要输入坐标那么我们就先定义x和y首先判断玩家输入的xy坐标合法在棋盘范围内如果合法就继续否则提示在玩家下棋时需要判断是否要下的位置为空格是空格说明当前位置没有棋子不是空格说明当前位置已被下棋就提示重新下棋
game.c
void PlayMove(char board[ROW][COL], int row, int col)
{int x 0;int y 0;printf(玩家下棋\n);while (1){printf(请输入坐标:);scanf(%d%d, x, y);if (x 1 x row y 1 y col){if (board[x - 1][y - 1] ){board[x - 1][y - 1] *;break;}else {printf(该坐标被占用请输入其他坐标\n);}}else {printf(坐标非法请重新输入\n);}}
}电脑下棋
电脑下棋要进行
game.h
#includetime.h
#includestdlib.h
void ComputerMove(char board[ROW][COL], int row, int col);test.c 在main函数里调用srand
srand((unsigned int)time(NULL));game函数
while (1)
{//玩家下棋PlayMove(board, ROW, COL);DisplayBoard(board, ROW, COL);//电脑随机下棋ComputerMove(board, ROW, COL);DisplayBoard(board, ROW, COL);
}game.c
电脑下棋也是同理调用rand函数随机生成一个数检测要下棋的位置是否为空格是空格才可以下不是空格重新生成一个随机数,重新下棋
void ComputerMove(char board[ROW][COL], int row, int col)
{printf(电脑下棋\n);int x 0;int y 0;x rand() % row;y rand() % col;while (1){if (board[x][y] ){board[x][y] #;break;}}
}这个时候就可以正常下棋了但是没有判断输赢下完了也不会结束而是死循环
判断输赢
判断输赢有四种状态
玩家赢电脑赢平局游戏继续 玩家赢返回* 电脑赢返回# 平局返回Q 游戏继续返回C game.h
char IsWin(char board[ROW][COL], int row, int col);这里判断输赢的时候首先玩家下棋进行判断有没有输赢然后电脑下棋如果有一方输赢了就进行返回
test.c
char ret 0;
while (1)
{//玩家下棋PlayMove(board, ROW, COL);DisplayBoard(board, ROW, COL);//判断输赢ret IsWin(board,ROW,COL);if (ret ! C){break;}//电脑随机下棋ComputerMove(board, ROW, COL);DisplayBoard(board, ROW, COL);ret IsWin(board, ROW, COL);if (ret ! C){break;}
}
if (ret *)
{printf(玩家赢\n);
}
else if (ret #)
{printf(电脑赢\n);
}
else
{pprintf(平局\n);
}这里是进行判断棋盘输赢的逻辑
game.c
int Is_Full(char board[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 (board[i][j] ){return 0; // 棋盘没满}}}return 1; // 棋盘满了
}char IsWin(char board[ROW][COL], int row, int col)
{int i 0;/* 判断三行 */for (i 0; i row; i){if (board[i][0] board[i][1] board[i][1] board[i][2] board[i][1] ! ){return board[i][1];}}/* 判断三列 */for (i 0; i col; i){if (board[0][i] board[1][i] board[1][i] board[2][i] board[1][i] ! ){return board[1][i];}}/* 判断对角线 */if (board[0][0] board[1][1] board[1][1] board[2][2] board[1][1] ! ){return board[1][1];}if (board[0][2] board[1][1] board[1][1] board[2][0] board[1][1] ! ){return board[1][1];}/* 判断平局 *///如果棋盘满了返回1 不满返回0if (Is_Full(board, row, col)){return Q;}/* 继续 */return C;
}四、结束
最后代码还是可以优化的比如判断输赢这里是写死了只能判断三行三列斜线如果是多行就不能了还有让电脑下棋智能一点能判断玩家下棋的位置再进行下棋这样更有可玩性 好了本文就到这里结束了下一篇是扫雷小游戏