Bootstrap

用C语言实现三子棋游戏

一、三子棋介绍

三子棋是一种民间传统游戏,又叫九宫棋、圈圈叉叉、一条龙等。将正方形对角线连起来,相对两边依次摆上三个双方棋子,只要将自己的三个棋子走成一条线,对方就算输了,但是三子棋很多时候会出现和棋的情况。

二、代码实现

1、设计思路 

我们在这里可以创建三个文件,分别为:

test.c //测试游戏的逻辑(主函数所在区)

game.c //游戏代码的实现(存放实现代码的函数)

game.h //游戏代码的声明

然后我们在代码中大致要完成以下功能:开始菜单、游戏实现、判断输赢。

2、开始菜单

在开始菜单中,我们要实现三个功能,分别是打印菜单、开始游戏和退出游戏。

//打印菜单
void meun() {
	printf("********************\n");
	printf("***1.play  2.exit **\n");
	printf("********************\n");
}

在完成了打印菜单后,我们可以将其放入test函数中,用do-while循环实现开始和退出游戏。输入1:开始游戏,输入0:退出游戏。 

void test() {
	void meun();
	void ber();
	char board[ROW][COL];
	int num = 0;
	srand((unsigned int)time(NULL));
	do {
		meun();
		
		printf("请输入:>>   ");
		scanf("%d", &num);
		switch (num) {
		case 1:
			ber();
			break;
		case 0:
			printf("退出游戏\n");
			break;
		default:
			printf("输入错误,请重新输入\n");
			break;
		}
	} while (num);
}

 3、游戏实现

游戏实现可分为三步:1.初始化棋盘。2.打印棋盘。3.玩家与电脑对弈。

1.初始化棋盘(在game.c中)
//初始化棋盘
void chushi(char board[ROW][COL], int row, int col) {
	int i = 0, j = 0;
	for (i = 0; i < row; i++) {
		for (j = 0; j < col; j++) {
			board[i][j] = ' ';
		}
	}
}

在这里,我们用‘   ’来初始化棋盘,会更为方便。其中board[ROW][COL]为存放棋盘中的各个元素的一个数组,ROW和COL为我们在game.h中定义的两个宏,代表棋盘的三行三列。

#define ROW 3
#define COL 3
2.打印棋盘(在game.c中)
//打印棋盘方格
void game(char board[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", 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");
		}
	}
}

打印棋盘的效果:

 

3.玩家与电脑对弈
(1)玩家下棋(在game.c中)
//玩家下棋
void player(char board[ROW][COL], int row, int col) {
	int x = 0;
	int y = 0;//玩家输入坐标落子
	printf("玩家下棋:>  ");
	while (1) {
		printf("请输入要下的坐标:");
		scanf("%d %d", &x, &y);
		if (x >= 1 && x <= 3 && y >= 1 && y <= 3) {
			if (board[x - 1][y - 1] == ' ') {  //判断该位置是否已下,没下落子,已下重新输入
				board[x - 1][y - 1] = '*';
				break;
			}
			else {
				printf("该位置已下,请重新输入!");
			}
		}
		else {
			printf("输入错误,请重新输入!");
		}
	}
}

 注意:这里要用while循环保证可多次下棋,每次落子后用break跳出循环,并且我们用 * 代表玩家的棋子。

(2)电脑下棋(在game.c中)
//电脑下棋
void computer(char board[ROW][COL], int row, int col) {
	int x=0;
	int y = 0;
	printf("电脑下棋>> \n");
	while(1){
		x = rand() % ROW;
		y= rand() % COL;
		if (board[x][y] == ' ') {
			board[x][y] = '#';
			break;
		}
	}
}

这里我们依旧用x,y表示棋子位置,值得注意的是,因为电脑是随机下棋,所以我们要的x和y是两个随机数,所以我们要用到rand()函数(用于产生随机数),又因为棋子的范围是0~2(数组原因),所以我们要使用%取余。(伴随着rand()函数的使用,我们还要用到time()和srand()函数(在test.c中),这三者配套使用)。电脑下棋我们用#表示。

来张对弈图:

4、判断输赢(在game.c中)

下棋时共有四种不同的情况:玩家赢、电脑赢、平局、继续游戏。因此我们可定义一个win函数,用它的返回值表示不同的情况。

//判断输赢
//电脑赢---#
//玩家赢---*
//继续---Q
//平局---C
char win(char board[ROW][COL], int row, int col) {
	int i = 0, j = 0;
	for (i = 0; i < row; i++) {
		for (j = 0; j < col; j++) {
			//判断横列
			if (board[i][0] == board[i][1] && board[i][1] == board[i][2] && board[i][0] != ' ')
				return board[i][0];
			//判断竖列
			if (board[0][j] == board[1][j] && board[1][j] == board[2][j] && board[0][j] != ' ')
				return board[0][j];
			//判断正叉
			if (board[0][0] == board[1][1] && board[1][1] == board[2][2] && board[0][0] != ' ')
				return board[0][0];
			//判断反叉
			if (board[0][2] == board[1][1] && board[1][1] == board[2][0] && board[2][0] != ' ')
				return board[2][0];
			//判断平局
			if (full(board, ROW, COL) == 1)
				return 'Q';
			//继续
			return 'C';
		}
	}
}

而平局判断则还需要一个判断棋盘是否下满的full函数来实现。

//判断是否下满
int full(char board[ROW][COL], int row, int col) {
	int i = 0, j = 0;
	for (i = 0; i < row; i++) {
		for (j = 0; j < col; j++) {
			if (board[i][j] == ' ') {
				return 0;
			}
		}
	}
	return 1;
}

下满返回1,未下满返回0。

三、完整代码

1、test.c部分

#include "game.h"
int main()
{
	void test();
	test();
}

void test() {
	void meun();
	void ber();
	char board[ROW][COL];
	int num = 0;
	srand((unsigned int)time(NULL));
	do {
		meun();
		
		printf("请输入:>>   ");
		scanf("%d", &num);
		switch (num) {
		case 1:
			ber();
			break;
		case 0:
			printf("退出游戏\n");
			break;
		default:
			printf("输入错误,请重新输入\n");
			break;
		}
	} while (num);
}
//打印菜单
void meun() {
	printf("********************\n");
	printf("***1.play  2.exit **\n");
	printf("********************\n");
}
//实现游戏
void ber() {
	char ret;
	char board[ROW][COL];
	//初始化棋盘
	chushi(board, ROW, COL);
	//打印棋盘方格
	game(board, ROW, COL);
	
	while (1) {
		
		//玩家下棋
		player(board, ROW, COL);
		game(board, ROW, COL);
		ret = win(board, ROW, COL);
		if (ret != 'C') {
			break;
		}
		//电脑下棋
		computer(board, ROW, COL);
		game(board, ROW, COL);
		ret = win(board, ROW, COL);
		if (ret != 'C') {
			break;
		}
	}
	if (ret == '*') {
		printf("玩家赢\n");
	}
	else if (ret == '#') {
		printf("电脑赢\n");
	}
	else {
		printf("平局\n");
	}
}

2、game.c部分

#include "game.h"
//初始化棋盘
void chushi(char board[ROW][COL], int row, int col) {
	int i = 0, j = 0;
	for (i = 0; i < row; i++) {
		for (j = 0; j < col; j++) {
			board[i][j] = ' ';
		}
	}
}
//打印棋盘方格
void game(char board[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", 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");
		}

	}
}
//玩家下棋
void player(char board[ROW][COL], int row, int col) {
	int x = 0;
	int y = 0;
	printf("玩家下棋:>  ");
	while (1) {
		printf("请输入要下的坐标:");
		scanf("%d %d", &x, &y);
		if (x >= 1 && x <= 3 && y >= 1 && y <= 3) {
			if (board[x - 1][y - 1] == ' ') {
				board[x - 1][y - 1] = '*';
				break;
			}
			else {
				printf("该位置已下,请重新输入!");
			}
		}
		else {
			printf("输入错误,请重新输入!");
		}
	}
}
//电脑下棋
void computer(char board[ROW][COL], int row, int col) {
	int x=0;
	int y = 0;
	printf("电脑下棋>> \n");
	while(1){
		x = rand() % ROW;
		y= rand() % COL;
		if (board[x][y] == ' ') {
			board[x][y] = '#';
			break;
		}
	}
}
//判断输赢
//电脑赢---#
//玩家赢---*
//继续---Q
//平局---C
char win(char board[ROW][COL], int row, int col) {
	int i = 0, j = 0;
	for (i = 0; i < row; i++) {
		for (j = 0; j < col; j++) {
			//判断横列
			if (board[i][0] == board[i][1] && board[i][1] == board[i][2] && board[i][0] != ' ')
				return board[i][0];
			//判断竖列
			if (board[0][j] == board[1][j] && board[1][j] == board[2][j] && board[0][j] != ' ')
				return board[0][j];
			//判断正叉
			if (board[0][0] == board[1][1] && board[1][1] == board[2][2] && board[0][0] != ' ')
				return board[0][0];
			//判断反叉
			if (board[0][2] == board[1][1] && board[1][1] == board[2][0] && board[2][0] != ' ')
				return board[2][0];
			//判断平局
			if (full(board, ROW, COL) == 1)
				return 'Q';
			//继续
			return 'C';
		}
	}
}
//判断是否下满
int full(char board[ROW][COL], int row, int col) {
	int i = 0, j = 0;
	for (i = 0; i < row; i++) {
		for (j = 0; j < col; j++) {
			if (board[i][j] == ' ') {
				return 0;
			}
		}
	}
	return 1;
}

3、game.h部分

#define ROW 3
#define COL 3
#include <stdio.h>
#include <stdlib.h>//srand()函数
#include<time.h>//time()函数
//定义函数
void game(char board[ROW][COL], int row, int col);
void chushi(char board[ROW][COL], int row, int col);
void player(char board[ROW][COL], int row, int col);
void computer(char board[ROW][COL], int row, int col);
//判断是否下满
int full(char board[ROW][COL], int row, int col);
//判断输赢
//电脑赢---#
//玩家赢---*
//继续---Q
//平局---C
char win(char board[ROW][COL], int row, int col);

 好了,以上就是三子棋游戏的实现。感谢各位看官的观看,如本篇内容对你有帮助,可以一键三连支持一下,感谢支持!!!

悦读

道可道,非常道;名可名,非常名。 无名,天地之始,有名,万物之母。 故常无欲,以观其妙,常有欲,以观其徼。 此两者,同出而异名,同谓之玄,玄之又玄,众妙之门。

;