前言
我们先来简单看一下三子棋实现的基本元素
首先我们可以看到,要想完成三子棋,就要有棋盘和棋子,棋盘是比较容易用打印打印出来的,关键是棋子的存放以及玩家与电脑之间下棋的步骤
提示:以下是本篇文章正文内容,下面案例可供参考
一、基本框架
我们要想实现这样一个人机交互的场景,就要先搭建出一个大致的基本框架
test.c文件
void menu()
{
printf("*********************\n");
printf("******1. play ******\n");
printf("******0. exit ******\n");
printf("*********************\n");
}
void game()
{
//三子棋游戏
}
int main()
{
int input = 0;
srand((unsigned int)time(NULL));
do
{
menu();
printf("请选择->:");
scanf("%d", &input);
switch (input)
{
case(1):
game();
break;
case(0):
printf("游戏退出!Bey\n");
break;
default:
printf("输入有误请重新输入:\n");
system("pause");
system("cls");
break;
}
} while (input);
}
二、实现game的基本框架
test.c文件
void game()
{
//存放棋子
char chess[ROW][COL] = { 0 };
//初始化棋子
set_chess(chess, ROW, COL);
//打印棋盘
print(chess, ROW, COL);
//玩家下棋--*
char ret = 0;
while (1)
{
play_chess(chess, ROW, COL);
print(chess, ROW, COL);
system("cls");
ret = is_win(chess, ROW, COL);//判断游戏是否结束
if (ret != 'C')
break;
computer_chess(chess, ROW, COL);
print(chess, ROW, COL);
if (ret != 'C')//同样进行一次判断
break;
}
if (ret == '*')
{
printf("玩家赢了\n");
}
else if (ret == '#')
{
printf("电脑赢了\n");
}
else
{
printf("平局\n");
}
print(chess, ROW, COL);
system("pause");
system("cls");
}
在game函数里面,我们设计了一个二维数组用来存放我们的棋子,同时在设计数组大小的时候,使用宏定义了两个常量ROW COL,这是为了方便我们之后在改变棋盘大小的时候,不用去一点点的修饰代码,极大的方便以后的一个使用
同时我们为了代码整体的一个整洁,使用了不同的文件来封装整个项目,我们把要引用的头文件都放在game.h中
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <windows.h>
#define ROW 3
#define COL 3
void set_chess(char chess[ROW][COL], int row, int col);
void print(char chess[ROW][COL], int row, int col);
void play_chess(char chess[ROW][COL], int row, int col);
void computer_chess(char chess[ROW][COL], int row, int col);
char is_win(char chess[ROW][COL], int row, int col);
把game游戏的实现代码放在game.c的源文件中
#include "game.h"
//初始化棋盘
void set_chess(char chess[ROW][COL], int row, int col)
{
int i = 0;
for (i = 0; i < row; i++)
{
int j = 0;
for (j = 0; j < col; j++)
{
chess[i][j] = ' ';
}
}
}
//打印棋盘
void print(char chess[ROW][COL], int row, int col)
{
int i = 0;
//打印棋盘号
printf(" ");
for (i = 1; i <= row; i++)
{
printf(" %d ", i);
}
printf("\n");
//打印棋盘
printf(" ");
for (i = 0; i < row; i++)
{
printf(" ---");
}
printf("\n");
for (i = 0; i < row; i++)
{
int j = 0;
printf("%d|", i+1);
for (j = 0; j < col; j++)
{
printf(" %c ", chess[i][j]);
if (j < col)
printf("|");
}
printf("\n");
//打印分割行
if (i < col)
{
printf(" ");
for (j = 0; j < col; j++)
{
printf(" ---");
}
}
printf("\n");
}
}
//玩家下棋
void play_chess(char chess[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 (chess[x - 1][y - 1] == ' ')
{
chess[x - 1][y - 1] = '*';
break;
}
else
{
printf("该坐标已被占用,请重新输入:\n");
}
}
else
{
printf("坐标非法,请重新输入:\n");
}
}
}
//电脑下棋
void computer_chess(char chess[ROW][COL], int row, int col)
{
printf("电脑走:\n");
while (1)
{
int x = rand() % row;
int y = rand() % col;
if (chess[x][y] == ' ')
{
chess[x][y] = '#';
break;
}
}
}
int if_full(char chess[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 (chess[i][j] == ' ')//棋盘未满
return 0;
}
}
return 1;//棋盘满
}
//判断游戏是否结束
char is_win(char chess[ROW][COL], int row, int col)
{
int i = 0;
for (i = 0; i < row; i++)//行
{
if (chess[i][0] == chess[i][1] && chess[i][1] == chess[i][2] && chess[i][0] != ' ')
return chess[i][0];
}
for (i = 0; i < col; i++)//列
{
if (chess[0][i] == chess[1][i] && chess[1][i] == chess[2][i] && chess[0][i] != ' ')
return chess[0][i];
}
//对角线
if (chess[0][0] == chess[1][1] && chess[1][1] == chess[2][2] && chess[0][0] != ' ')
return chess[0][0];
if (chess[2][0] == chess[1][1] && chess[1][1] == chess[0][2] && chess[0][2] != ' ')
return chess[2][0];
//平局
if (if_full(chess, row, col) == 1)
{
return 'Q';//返回什么都无所谓,只要是char就行
}
//如果以上情况都没有,那么返回C继续下棋
return 'C';
}
这样做的好处是,方便日后对代码进行优化和查看。
总结
关于要在实现game.c代码中的注意事项,我都在其中进行了注释,方便大家理解
关于电脑下棋的优化,我这里给大家提一下优化方案
当我们将上面的代码进行测试一遍之后不难发现,电脑在下棋的时候并不会对我们即将连成一条线的时候进行堵截,这是我们在写程序的时候并没有告诉电脑三子棋得规则,它只会在棋盘中进行简单的落子,那么如果我们在写电脑下棋的代码的时候,给加上一个判断,告诉它在我们有两个子已经在一条直线上的时候,对我们进行一个堵截(让电脑下在我们即将要连成一条线的位置),那么就会形成电脑对我们进行堵截的一个情况。
如果电脑发现我们没有两个子在一条直线上时,就考虑自己是否有两个子在一条直线上,如果有,就下在那个位置赢取游戏。
基本思路有了之后,我们只需要考虑有哪几种情况(我大致算了一下大概有十几种)符合要求,在写电脑下棋的之前,用if语句进行一个判断就可以了,不难实现,但是代码量很多,感兴趣的小伙伴可以试一下
最后有不懂的地方可以给我留言或者私信哦