【C语言】三子棋游戏

简介: 三子棋游戏

文件分装

image.png


test.c:放置主函数(main())和菜单函数(menu())和游戏函数(game())。

game.c:放置game()里面的相应操作的函数,例如玩家移动(PlayerMove(board)),电脑移动(ComputerMove(board)),以及每一次移动之后打印当前棋盘内容的函数(DisplayBoard(board))等等。由于这些函数内容较多,所以单独放在一个头文件里实现。

game.h:放置game.c里面函数的声明,以及需要用到的库函数的头文件(stdio.h,stdlib.h,time.h),在test.c和game.c中引用即可(#include " game.h ")

对应文件的代码

test.c

1.主函数(main () )

游戏的大体执行流程


int main()
{
  //设置随机数生成起点,作为后面电脑下子时的坐标
  srand((unsigned int)time(NULL));
  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;
}


2.菜单函数(menu())

玩家选择玩游戏或者退出


void menu()
{
  printf("***************************************\n");
  printf("***   1.play               0.exit   ***\n");
  printf("***************************************\n");
}


3.游戏函数(game () )


三子棋游戏的操作步骤,里面涉及到的函数会在game.c说明

void game()
{
  //作为标志判断最后结果的标志
  int ret = 0;
  //设置存放棋盘信息的数组
  char board[3][3] = { 0 };
  //初始化棋盘内容全部为空格
  InitBoard(board);
  //打印棋盘
  DisplayBoard(board);
  //下棋
  //下棋过程
  while (1)
  {
  //玩家下子
  PlayerMove(board);
  DisplayBoard(board);
  ret = IsWin(board);
  //若ret=='c'就继续下棋,其他的就是玩家赢或者电脑赢或者平局就停止下棋,跳出while循环
  if ('c' != ret)
    break;
  //电脑下子
  ComputerMove(board);
  DisplayBoard(board);
  ret = IsWin(board);
  if ('c' != ret)
    break;
  }
  //下棋结束,判断谁赢了
  if ('*' == ret)
  printf("玩家赢\n");
  else if ('#' == ret)
  printf("电脑赢\n");
  else if('e'==ret)
  printf("平局\n");
}


game.c

ps:里面的p数组指针,实参为board,即棋盘第一行数组的地址


1. InitBoard(初始化棋盘内容)


//初始化棋盘内容全部为空格
void InitBoard(char (*p)[3])
{
  int i = 0;
  for (i = 0; i < 3; i++)
  {
  int j = 0;
  for (j = 0; j < 3; j++)
  {
    p[i][j] = ' ';
  }
  }
}


2.DisplayBoard(展示棋盘内容)

开始时的棋盘是这样的

void DisplayBoard(char (*p)[3])
{
  int i = 0;
  //棋盘每行的打印
  for (i = 0; i < 3; i++)
  {
  //打印棋子和竖杆
  printf(" %c | %c | %c \n", p[i][0], p[i][1], p[i][2]);
  //分隔行只用打印两行
  if (i < 2)
    printf("---|---|---\n");
  }
}


3.PlayerMove(玩家下子)

玩家下的子用*表示,需要注意两点1.下的子是否在棋盘坐标内 2.该坐标是否已经被下子。


//玩家下子(*)
void PlayerMove(char (*p)[3])
{
  int x = 0;
  int y = 0;
  printf("玩家走:>\n");
  while (1)
  {
  printf("请输入要下的坐标(有空格隔开):>");
  scanf("%d%d", &x, &y);
  //判断坐标是否正确
  if (x >= 1 && x <= 3 && y >= 1 && y <= 3)
  {
    //若下子坐标正确,再判断该坐标是否已经被下子
    if (p[x-1][y-1]==' ')
    {
    p[x-1][y-1] = '*';
    break;
    }
    else
    {
    printf("该位置已经被下子\n");
    }
  }
  else
  {
    printf("坐标输入错误\n");
  }
  }
}


4.ComputerMove(电脑下子)

电脑下的子用#表示,通过限定rand函数得到的下子坐标肯定是在棋盘内了,只需考虑该坐标是否已经被下子。


//电脑下子(#)
void ComputerMove(char (*p)[3])
{
  int x = 0;
  int y = 0;
  printf("电脑走:>\n");
  //下子坐标已经有效,只需判断该坐标是否已经被下子
  while (1)
  {
  //令x和y随机生成一个0-2之间的数来作为电脑下子的坐标
  int x = rand() % 3;
  int y = rand() % 3;
  //判断是否已经被下子
  if (' ' == p[x][y])
  {
    p[x][y] = '#';
    break;
  }
  }
}



5.IsWin(判断输赢)和IsFull(判断棋盘是否已经被下满)

每下一步棋都有四种情况,玩家赢,电脑赢,平局,继续,通过IsWin来判断:


判断谁赢:棋盘三行或者三列或者两条对角线都是同一种棋子,谁赢了就返回他所下的棋子的符号(*或者#)

要是都没赢的话只剩两种情况平局(棋盘下满了)和继续(棋盘没下满),通过IsFull来判断当前棋盘是否满了来决定是否继续下棋。

//判断棋盘是否已经下满
//下满返回1
//没下满返回0
int IsFull(char(*p)[3])
{
  int i = 0;
  int j = 0;
  for (i = 0; i < 3; i++)
  {
  for (j = 0; j < 3; j++)
  {
    if (p[i][j] == ' ')
    return 0;
  }
  }
  return 1;
}
//判断输赢
//玩家赢了返回'*'
//电脑赢了返回'#'
//平局返回'e'
//继续返回'c'
char IsWin(char(*p)[3])
{
  int i = 0;
  //横三行
  for (i = 0; i < 3; i++)
  {
  if (p[i][0] == p[i][1] && p[i][1] == p[i][2] && p[i][0] != ' ')
    return p[i][0];
  }
  //竖三列
  for (i = 0; i < 3; i++)
  {
  if (p[0][i] == p[1][i] && p[1][i] == p[2][i] && p[0][i] != ' ')
    return p[0][i];
  }
  //两个对角线
  if (p[0][0] == p[1][1] && p[1][1] == p[2][2] && p[0][0] != ' ')
  return p[0][0];
  if (p[0][2] == p[1][1] && p[1][1] == p[2][0] && p[0][2] != ' ')
  return p[0][2];
  //判断平局还是继续(电脑和玩家都没赢。此时棋盘满了就平局,没满就继续)
  if (IsFull(p))
  return 'e';
  else
  return 'c';
}


game.h

包括函数的声明和需要用到的C语言的库函数


#include<stdio.h>
#include<stdlib.h>
#include<time.h>
void InitBoard(char (*p)[3]);
void DisplayBoard(char (*p)[3]);
void PlayerMove(char (*p)[3]);
void ComputerMove(char (*p)[3]);
char IsWin(char (*p)[3]);
相关文章
|
1月前
|
C语言
扫雷游戏(用C语言实现)
扫雷游戏(用C语言实现)
97 0
|
3月前
|
机器学习/深度学习 C语言
九/十:《初学C语言》— 扫雷游戏实现和函数递归基础
【8月更文挑战第5天】本篇文章用C语言采用多文件编写实现了一个基础的扫雷游戏(附源码),并讲解了关于函数递归的基础概念及其相对应的习题练习(附源码)
42 1
九/十:《初学C语言》— 扫雷游戏实现和函数递归基础
|
13天前
|
C语言 Windows
C语言课设项目之2048游戏源码
C语言课设项目之2048游戏源码,可作为课程设计项目参考,代码有详细的注释,另外编译可运行文件也已经打包,windows电脑双击即可运行效果
25 1
|
4月前
|
存储 C语言 开发者
C语言实战 | Flappy Bird游戏
【7月更文挑战第4天】Flappy Bird是由越南开发者制作的简单却极具挑战性的游戏,玩家需控制小鸟穿越水管障碍。游戏涉及角色初始化、显示和更新。小鸟和水管结构体存储数据,使用变量和数组。初始化小鸟和水管,显示背景、小鸟和水管,更新小鸟位置及碰撞检测。代码示例展示了小鸟和水管的状态管理,当小鸟与管道碰撞或触地时,游戏结束。游戏的成功在于其独特的虐心体验。
79 0
C语言实战 | Flappy Bird游戏
|
1月前
|
编译器 C语言
猜数字游戏实现#C语言
猜数字游戏实现#C语言
82 1
|
1月前
|
存储 C语言
揭秘C语言:泊舟的猜数字游戏
揭秘C语言:泊舟的猜数字游戏
|
1月前
|
存储 算法 安全
C语言实现扫雷游戏
C语言实现扫雷游戏
|
1月前
|
算法 编译器 C语言
【C语言】实现猜数字游戏(分支语句与循环语句的运用)
【C语言】实现猜数字游戏(分支语句与循环语句的运用)
|
1月前
|
C语言
初学者指南:使用C语言实现简易版扫雷游戏
初学者指南:使用C语言实现简易版扫雷游戏
37 0
|
1月前
|
C语言
C语言扫雷游戏(详解)
C语言扫雷游戏(详解)
40 0