前言
首现实现三子棋,我们要知道三子棋的玩法及规则
三子棋,民间传统游戏,又叫九宫棋、圈圈叉叉、一条龙等;
获胜判定:只要电脑或者玩家任意一方的棋子有三子连在一起,可以为横连、纵连、斜连,则该方获胜,游戏结束。若棋盘满了,则判定为平局。
游戏规则要求:电脑(随机)和玩家一次下一子,双方轮流交替下子,直到电脑和玩家任意一方获胜,或者棋盘满了,结束游戏。
注:玩家下棋是 '*' 电脑下棋是 '#'
实现程序的思路:
1.游戏菜单:选择是否开始玩儿游戏,1:玩儿,0:退出游戏;
2.初始化棋盘
3.打印棋盘
4.下棋
5.判断输赢
在实现之前,首先创三个文件来实现,包含三部分来实现代码
注:本人用的是Visual 2019开发工具实现
1. text.c 测试游戏的逻辑
2. game.c 用来写有关游戏实现的函数
3. game.h 用来函数声明,符号的定义
开始写代码并进行调试
开始之前先来说下定义符号常量,放到game.h头文件上,实现是3*3的棋盘,在头文件game.h这样写的好处是以后想实现4*4 , 5*5等等,直接这里改,其它文件要想用引用头文件就行了
#define ROW 3
#define COL 3
主函数的整体设计,代码如下
int main()
{
int input = 0;
do
{
mven();
printf("请选择菜单->");
scanf("%d", &input);
switch (input)
{
case 1:
game();
break;
case 0:
printf("退出游戏\n");
break;
default:
printf("输入错误请重新选择\n");
break;
}
} while (input);
return 0;
}
menu()用来实现游戏菜单,代码如下
void mven()
{
printf("**************************\n");
printf("******** 1.play **********\n");
printf("******** 2.stop **********\n");
printf("**************************\n");
}
这是大体的逻辑,能走起来了,接下来实现游戏设计的函数,用game()来实现游戏
1.接下来要干什么呢,既然是下棋,首先是不是要初始棋盘,看是不者是空格,所以初始化都为空格
//用来初始棋盘
void initial_chessboard(char borad[ROW][COL], int row, int col);
代码实现,这里用两个循环来初始化空格
void initial_chessboard(char borad[ROW][COL], int row, int col)
{
int i = 0;
for ( i = 0; i < row; i++)
{
int j = 0;
for ( j = 0; j < col; j++)
{
borad[i][j] = ' ';
}
}
}
2.初始化棋盘后,就是打印棋盘了
看都是由空格和 |,---组成的棋盘 ,下面我们来打印下
//用来打印棋盘
void print_chessboard(char borad[ROW][COL], int row, int col);
void print_chessboard(char borad[ROW][COL], int row, int col)
{
int i = 0;
for (i = 0; i < row; i++)
{
int j = 0;
for ( j = 0; j < col; j++)
{
printf(" %c ", borad[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");
}
}
}
写成这样就可以打印各种棋盘了,打印出来就这样了
3.初始棋盘及打印棋盘,接下来可以开始下棋了,下棋时,肯定是玩家一步,电脑一步
我们先来实现玩家下棋的代玛先
//玩家下棋
void Players_play_chess(char borad[ROW][COL], int row, int col);
void Players_play_chess(char borad[ROW][COL], int row, int col)
{
int x = 0;
int y = 0;
while (1)
{
printf("玩家下棋->");
scanf("%d %d", &x, &y);
// 下棋之前还要判断代码的合法性
if (x >= 1 && x <= row && y >= 1 && y <= col)
{
//判断棋盘是否满了
if (borad[x-1][y-1]==' ')
{
borad[x-1][y-1] = '*';
break;
}
else
{
printf("该坐标已占用,请输入\n");
}
}
else
{
printf("非法输入,请重新输入\n");
}
}
}
下棋之前还要判断代码的合法性,还有这里的代码是面用户的,他们不知道什么数组下标是0,所以
这里写成borad[x-1][y-1],这样坐标就从1开始了
接下来就是电脑下棋了
//电脑下棋
void Man_machine_chess(char borad[ROW][COL], int row, int col);
void Man_machine_chess(char borad[ROW][COL], int row, int col)
{
printf("电脑下棋->\n");
while (1)
{
//生成随机坐标
int x = rand() % row;
int y = rand() % col;
//判断棋盘是否满了
if (borad[x][y] == ' ')
{
borad[x][y] = '#';
break;
}
}
}
因为电脑是人机的,所以他所下棋的位置是比较随机的,同时我们还要注意这里rand() 函数是生成随机数,因为电脑下棋坐标是(0,0)到(2,2)(这里是以二维数组来说),所以rand()%3 即可,这样随机数的范围就是0-2了,同时使用了rand就需要srand配合使用,不然就是伪随机数了
要在主函数增加这个语句
srand((unsigned)time(NULL));
(这里简单说下rand 函数随机数范围确定,ranf ()%row,生成随机数的范围就是0到row-1)
4.判断胜负
什么情况,游戏结束了
我们这样
1.玩家赢了返回 '*'
2.电脑赢了 返回 '#'
3.平局 返回 'Q'
4.继续 返回 'C'
//判断输赢
char is_win(char borad[ROW][COL], int row, int col);
char is_win(char borad[ROW][COL], int row, int col)
{
//判断行
int i = 0;
for ( i = 0; i < row; i++)
{
if (borad[i][0]== borad[i][1] && borad[i][1]== borad[i][2] && borad[i][1] != ' ')
{
return borad[i][1];
}
}
//判断列
int j = 0;
for ( j = 0; j < col; j++)
{
if (borad[0][i] == borad[1][i] && borad[1][i] == borad[2][i] && borad[1][i] != ' ')
{
return borad[1][j];
}
}
//判断对角线
if (borad[0][0] == borad[1][1] && borad[1][1] == borad[2][2] && borad[1][1] != ' ')
{
return borad[1][1];
}
if (borad[0][2] == borad[1][1] && borad[1][1] == borad[2][0] && borad[1][1] != ' ')
{
return borad[1][1];
}
//判断平局
if (if_full(borad,row,col)==1)
{
return 'C';
}
return 'Q';
}
5.判断平局代码
int if_full(char borad[ROW][COL], int row, int col)
{
int i = 0;
for (i = 0; i < row; i++)
{
int j = 0;
for (j = 0; j < col; j++)
{
if (borad[i][j] == ' ')
{
return 1;//没满返回1
}
}
}
return 0;//满了返回0
}
6.就进行胜利判断
if (ret == '*')
{
printf("玩家赢了\n");
}
else if (ret == '#')
{
printf("电脑赢了\n");
}
else
{
printf("平局\n");
}
7.运行图例
8.全部代码如下
(1)text.c文件
#include"game.h"
void mven()
{
printf("**************************\n");
printf("******** 1.play **********\n");
printf("******** 2.stop **********\n");
printf("**************************\n");
}
void game()
{
char ret = 0;
char borad[ROW][COL] = { 0 };
//初始棋盘为空格
initial_chessboard(borad, ROW, COL);
//打印棋盘
print_chessboard(borad, ROW, COL);
while (1)
{
//用来实现玩家下棋
Players_play_chess(borad, ROW, COL);
print_chessboard(borad, ROW, COL);
//判断输赢
//什么情况,游戏结束了 1.玩家赢了 - '*' 2.电脑赢了 - '#'
//3.平局 - 'Q' 4.继续 - 'C'
ret =is_win(borad, ROW, COL);
if (ret != 'C')
{
break;
}
//用来实现电脑下棋
Man_machine_chess(borad, ROW, COL);//随机下
print_chessboard(borad, ROW, COL);
ret = is_win(borad, ROW, COL);
if (ret != 'C')
{
break;
}
}
if (ret == '*')
{
printf("玩家赢了\n");
}
else if (ret == '#')
{
printf("电脑赢了\n");
}
else
{
printf("平局\n");
}
print_chessboard(borad, ROW, COL);//最后在打印下棋盘看下
}
int main()
{
srand((unsigned int)time(NULL));
int input = 0;
do
{
mven();
printf("请选择菜单->");
scanf("%d", &input);
switch (input)
{
case 1:
game();
break;
case 0:
printf("退出游戏\n");
break;
default:
printf("输入错误请重新选择\n");
break;
}
} while (input);
return 0;
}
(2)game.c文件
#include"game.h"
#include<stdio.h>
void initial_chessboard(char borad[ROW][COL], int row, int col)
{
int i = 0;
//初始化棋盘
for ( i = 0; i < row; i++)
{
int j = 0;
for ( j = 0; j < col; j++)
{
//用空格初始化
borad[i][j] = ' ';
}
}
}
void print_chessboard(char borad[ROW][COL], int row, int col)
{
int i = 0;
//打印棋盘
for (i = 0; i < row; i++)
{
int j = 0;
for ( j = 0; j < col; j++)
{
printf(" %c ", borad[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");
}
}
}
void Players_play_chess(char borad[ROW][COL], int row, int col)
{
int x = 0;
int y = 0;
while (1)
{
printf("玩家下棋->");
scanf("%d %d", &x, &y);
//判断是否是有效坐标
if (x >= 1 && x <= row && y >= 1 && y <= col)
{
//判断是否为空格,是就打印*不是重新输入
if (borad[x-1][y-1]==' ')
{
borad[x-1][y-1] = '*';
break;
}
else
{
printf("该坐标已占用,请输入\n");
}
}
else
{
printf("非法输入,请重新输入\n");
}
}
}
void Man_machine_chess(char borad[ROW][COL], int row, int col)
{
printf("电脑下棋->\n");
while (1)
{
//生成0-2的随机数坐标
int x = rand() % row;
int y = rand() % col;
//判断是否为空格,是就打印#
if (borad[x][y] == ' ')
{
borad[x][y] = '#';
break;
}
}
}
static int if_full(char borad[ROW][COL], int row, int col)
{
int i = 0;
for (i = 0; i < row; i++)
{
int j = 0;
for (j = 0; j < col; j++)
{
if (borad[i][j] == ' ')
{
return 1;//没满
}
}
}
return 0;//满了
}
char is_win(char borad[ROW][COL], int row, int col)
{
//判断行
int i = 0;
for ( i = 0; i < row; i++)
{
if (borad[i][0]== borad[i][1] && borad[i][1]== borad[i][2] && borad[i][1] != ' ')
{
return borad[i][1];
}
}
//判断列
int j = 0;
for ( j = 0; j < col; j++)
{
if (borad[0][i] == borad[1][i] && borad[1][i] == borad[2][i] && borad[1][i] != ' ')
{
return borad[1][j];
}
}
//判断对角线
if (borad[0][0] == borad[1][1] && borad[1][1] == borad[2][2] && borad[1][1] != ' ')
{
return borad[1][1];
}
if (borad[0][2] == borad[1][1] && borad[1][1] == borad[2][0] && borad[1][1] != ' ')
{
return borad[1][1];
}
//判断平局
if (if_full(borad,row,col)==1)
{
return 'C';
}
return 'Q';
}
(3)game.h文件
#include<stdio.h>
#include<stdlib.h>
#include<time.h>
#define ROW 3
#define COL 3
//声明
//初始棋盘
void initial_chessboard(char borad[ROW][COL], int row, int col);
//打印棋盘
void print_chessboard(char borad[ROW][COL], int row, int col);
//玩家下棋
void Players_play_chess(char borad[ROW][COL], int row, int col);
//电脑下棋
void Man_machine_chess(char borad[ROW][COL], int row, int col);
//判断输赢
char is_win(char borad[ROW][COL], int row, int col);
9.小结
游戏实现利用了二维数组,随机数,函数等知识进行实现
基本能实现三子棋游戏,代码已奉上,有不足之处望指教!