c语言实现三子棋(内含阅读思路,简单易实现)

简介: 本文如果按顺序来阅读可能不太好接受,建议阅读顺序为,由test.c的逻辑顺序读下去,遇见具体函数的实现跳转到game.c中来理解

接下来就是通过c语言来实现三子棋这个小游戏,这个游戏是通过分文件写的方法来实现的,这种方法可增强代码的可读性,让我们一起来康康吧!


本文如果按顺序来阅读可能不太好接受,建议阅读顺序为,由test.c的逻辑顺序读下去,遇见具体函数的实现跳转到game.c中来理解


注:


test.c文件实现游戏的逻辑
game.c文件实现游戏中操作的具体实现(封装函数的实现)
game.h文件为整个游戏的头文件(用于声明)

game.h


#include<stdio.h>//用于函数引用的头文件
#include<stdlib.h>//用于函数引用的头文件
#include<time.h>//用于函数引用的头文件
#define ROW 3//棋盘行数
#define COL 3//棋盘列数
void InitBoard(char board[ROW][COL], int row, int col);//初始化棋盘
void DisplayBoard(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 IsWin(char board[ROW][COL], int row, int col);//判断游戏状态


test.c(游戏逻辑实现)


整个游戏的逻辑从main函数开始(具体实现在代码旁的注释说明)


#include"game.h"
void menu()//打印菜单
{
  printf("****************\n");
  printf("*****1.play*****\n");
  printf("*****0.exit*****\n");
  printf("****************\n");
}
void game()
{
  char ret = 0;//用于记录实时游戏情况
  char board[ROW][COL] = { 0 };//定义三子棋棋盘
  InitBoard(board,ROW,COL);//初始化棋盘
  DisplayBoard(board, ROW, COL);//打印棋盘
    /*
    各自下一步棋后打印棋盘,然后判断游戏进程,只有游戏结束时才会跳出循环
    以下为逻辑实现,每一步操作需读者跳转到game.c文件中理解
    */
  while (1)
  {
  PlayerMove(board, ROW, COL);//玩家下棋
  DisplayBoard(board, ROW, COL);//实时打印棋盘
  ret= IsWin(board, ROW, COL);//实时判断游戏进程
  if (ret != 'C')//只有返回值不是‘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
  {
  printf("平局\n");
  }
}
int main()
{
  int input = 0;
  srand((unsigned int)time(NULL));//此处先不解释,后边解释
  do //设置循环,每次输入一个数,1进入游戏,0退出游戏
  {
  menu();//打印菜单
  scanf("%d", &input);
  switch (input)
  {
  case 1:
    printf("开始游戏\n");
    game();//如果输入1,进入游戏,游戏的进一步实现在game()函数中
    break;
  case 0:
    printf("退出游戏\n");
    break;
  default:
    printf("输入错误,请重新输入\n");
    break;
  }
  } while (input);//如果输入0,while循环终止,退出游戏
}


game.c


初始化棋盘


需要将3*3数组先全部置成空格,才能打印出空白棋盘


void InitBoard(char board[ROW][COL], int row, int col)
{
  for (int i = 0; i < row; i++)
  {
  for (int j = 0; j < col; j++)
    board[i][j] = ' ';
  }


打印棋盘


打印出的棋盘应为这副模样


微信图片_20230110145729.png

void DisplayBoard(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++)
  {
    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 PlayerMove(char board[ROW][COL], int row, int col)
{
  printf("玩家下棋\n");
  int x=0, y=0;
  while (1)//设置循环,当玩家下好棋后终止循环
  {
  printf("请输入你要下的位置>\n");
  scanf("%d %d", &x, &y);
  if (x >= 1 && x <= ROW && y >= 1 && y <= COL)//注意数组的行列都比棋盘行列少1
  {
    if (board[x - 1][y - 1] == ' ')//如果此处无棋,将这个位置变成‘*’
    {
    board[x - 1][y - 1] = '*';
    break;//下棋完成跳出循环
    }
    else
    printf("你输入的位置已被占用,请重新输入\n");
  }
  else
    printf("你输入的位置不合法,请重新输入\n");
  }
}


电脑下棋


void ComputerMove(char board[ROW][COL], int row, int col)
{
  printf("电脑下棋>\n");
  int x = 0, y = 0;
  while (1)
  {
  x = rand() % ROW;//x,y为对3取余数的随机值即0~2
  y = rand() % COL;
  if (board[x][y] == ' ')//如果该位置为空,将棋下于此
  {
    board[x][y] = '@';
    break;
  }
  }
}


判断游戏进程


游戏结果无非三种:赢 输 平


返回不同的结果:


‘C’继续游戏


‘Q’平局


‘*’玩家赢


‘@’电脑赢


static IsFull(char board[ROW][COL], int row, int col)//判断棋盘是否满了
{
  for (int i = 0; i < row; i++)
  {
  for (int 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][2] != ' ')
    return board[i][2];
  }
  for (i = 0; i < col; i++)//列
  {
  if (board[0][i] == board[1][i] && board[1][i] == board[2][i] && board[2][i] != ' ')
    return board[2][i];
  }
  //对角线
  if (board[0][0] == board[1][1] && board[1][1] == board[2][2] && board[2][2] != ' ')
  return board[1][1];
  if (board[0][2] == board[1][1] && board[1][1] == board[2][0] && board[2][0] != ' ')
  return board[1][1];
    /*
    行 列 对角线都是返回的对应图案,及对应不同玩家赢得游戏
    */
  if (IsFull(board, ROW, COL))//如果没有分出胜负但是棋盘满了,则为平局
  return 'Q';
  return 'C';//如果前边都没有返回,就返回'C',继续游戏
}


相关文章
|
2月前
|
C语言
c语言简单三子棋
c语言简单三子棋
|
2月前
|
C语言
以c语言为基础实现的简易三子棋
以c语言为基础实现的简易三子棋
26 1
|
2月前
|
算法 C语言 C++
【C语言实战项目】三子棋游戏
【C语言实战项目】三子棋游戏
42 1
|
2月前
|
C语言
C语言之三子棋小游戏
C语言之三子棋小游戏
|
2月前
|
C语言
用c语言实现三子棋
用c语言实现三子棋
15 0
|
9天前
|
C语言
【海贼王编程冒险 - C语言海上篇】C语言如何实现简单的三子棋游戏?
【海贼王编程冒险 - C语言海上篇】C语言如何实现简单的三子棋游戏?
8 1
|
13天前
|
存储 C语言
三子棋(C语言版)
三子棋(C语言版)
|
2月前
|
C语言
万字详解:C语言三子棋进阶 + N子棋递归动态判断输赢(二)
我们可以通过创建并定义符号常量NUMBER,来作为判断是否胜利的标准。如三子棋中,令NUMBER为3,则这八个方向中有任意一个方向达成3子连珠,则连珠的这个棋子所代表的玩家获胜。
28 1
|
2月前
|
算法 C语言 C++
万字详解:C语言三子棋进阶 + N子棋递归动态判断输赢(一)
三子棋游戏设计的核心是对二维数组的把握和运用。
29 1
|
2月前
|
编译器 C语言
【C语言入门小游戏】三子棋
【C语言入门小游戏】三子棋
28 0
【C语言入门小游戏】三子棋