两百行代码实现c语言的五子棋小游戏,课程设计用。

合肥城市学院

课程设计报告书

设计题目

   五子棋游戏的设计与实现

院(系)名称:

专业班级

学生姓名

学  号

          

指导教师

课程设计报告

1. 功能性需求:

   - 实现一个简单的五子棋游戏,支持人机对战模式。

   - 游戏界面应包含开始和结束选项的菜单功能。

   - 程序能初始化一个5x5的棋盘,并以空格表示未落子位置。

   - 玩家可以输入坐标进行落子操作,程序需验证坐标合法性及位置是否已被占用。

   - 电脑玩家(AI)随机选择棋盘上的空位进行落子。

   - 程序应具备判断游戏结束的功能,包括检测是否存在获胜者(横向、纵向或对角线方向的连续五个相同标记)以及棋盘填满时宣布平局。

2. 性能需求:

   - 游戏运行流畅,响应时间短,无明显延迟,如:玩家输入坐标后,计算机能快速做出反应并完成落子操作。

   - AI落子算法虽为随机选择,但应确保在合理的时间内完成决策。

3. 可靠性和可用性需求:

   - 程序应保证在各种正常和异常情况下都能稳定运行,不出现崩溃现象。

   - 输入验证机制要健全,确保所有用户输入均能得到有效处理,防止因非法输入导致程序错误。

   - 提供清晰的游戏状态输出,例如通过打印棋盘来展示当前游戏局势,方便玩家理解游戏进展。

4. 出错处理需求:

   - 当玩家输入非法坐标时,程序应提示玩家重新输入,而不是直接退出或卡死。

   - 如果发生意外情况导致程序无法继续运行,应提供适当的错误信息并确保程序能够安全终止,比如释放已分配的内存资源。

   - 对于可能发生的边界条件错误(如数组越界访问),代码中已经通过循环变量控制进行了预防。但仍需确保所有涉及数组索引的操作都有相应的边界检查。

 

 

1. 引言

   1.1 编写目的:本代码旨在实现一个基于命令行界面的五子棋游戏,支持玩家与电脑对弈。

   1.2 背景:为了提供一个简单易用且具有趣味性的编程实践项目,该代码采用C语言编写,适用于学习数据结构、控制流和人机交互基础的学生练习。

   1.3 定义:

      - ROW/COL:定义棋盘大小为5x5

      - g_broad:全局变量,用于存储棋盘状态,其中' '表示空位,'x'表示玩家落子,'o'表示电脑落子

   1.4 参考资料:此代码主要参考了标准C库函数,包括输入输出、随机数生成以及时间获取等。

2. 总体设计

   2.1 需求规定:

      - 提供菜单选项以开始或结束游戏

      - 初始化并展示5x5棋盘

      - 玩家与电脑交替落子

      - 检查并宣布获胜者或平局

   2.2 运行环境:Windows操作系统,兼容C语言编译器(如GCC或MSVC),控制台环境

   2.3 基本设计概念和处理流程:

      - 使用函数封装各个模块功能,如初始化棋盘、打印棋盘、玩家落子、电脑落子、检查获胜者及判断棋盘是否已满

      - 主循环中,先打印棋盘,然后执行玩家和电脑的落子操作,并在每次落子后检查游戏是否结束

   2.4 系统架构:程序采用单线程、顺序执行的方式进行,包含多个函数协同完成整个游戏逻辑

   2.5 功能需求与程序的关系:每个函数对应一项具体的功能需求,通过主函数调用各功能函数串联起完整的五子棋游戏流程

3. 系统数据结构设计

   3.1 逻辑结构设计要点:使用二维字符数组g_broad作为核心数据结构来存储棋盘状态信息

   3.2 物理结构设计要点:棋盘的物理结构直接映射到内存中的二维数组布局,便于高效访问和更新棋盘状态

   3.3 数据结构与程序的关系:所有关于棋盘的操作,包括初始化、打印、落子以及胜负判断等功能,均围绕着这个二维字符数组进行。

以下是基于您提供的代码所构建的简易功能模块结构描述和流程图简述:

**功能模块结构:**

1. **主控模块(main**

   - 功能:负责启动游戏、初始化棋盘、接收用户输入、调用各子模块进行游戏循环,并在游戏结束后输出结果。

2. **菜单显示模块(menu**

   - 功能:显示开始游戏和结束游戏的选项供用户选择。

3. **棋盘初始化模块(Init**

   - 功能:将全局二维字符数组`g_broad`中的所有元素设置为空格(' '),表示棋盘状态为空。

4. **棋盘打印模块(print**

   - 功能:以特定格式输出当前棋盘的状态。

5. **玩家落子模块(playermove**

   - 功能:接收玩家输入的坐标,验证其合法性后,在棋盘上放置玩家棋子('x')。

6. **电脑落子模块(computermove**

   - 功能:随机选取一个空位,在棋盘上放置电脑棋子('o')。

7. **判断棋盘是否已满模块(Isfull**

   - 功能:检查棋盘上的所有位置是否都被占用。

8. **检查获胜者模块(checkwinner**

   - 功能:根据五子棋规则检测棋盘上是否存在连续五个相同标记('x''o'),或者棋盘是否已满以判断胜负和平局。

流程图简述:

```

  开始

    |

    V

[主控模块]——>[菜单显示模块]

    |                     |

    | (选择开始游戏)     |

    V                     |

[棋盘初始化模块]——>[打印棋盘模块]

    |                     |

    |                     |

(进入游戏循环)         |

    V                     V

[打印棋盘模块]——>[玩家落子模块]——>[检查获胜者模块]

    |        |                    |

    |        | (无胜者)           |

    |        V                    |

    |       [电脑落子模块]——>[检查获胜者模块]

    |        |                    |

    |        | (有胜者/棋盘已满)  |

    |        V                    |

    |       [宣布胜负/平局]      |

    |        |                    |

    |        | (继续游戏)         |

    |        V                    |

    +---------------------------| (重复以上步骤直至游戏结束)

                                 |

                                 V

                            [游戏结束,输出告别信息]

```

  系统流程图:

图4是一个流程图,描述了五子棋游戏的运行过程:

1. **开始阶段**

   - 初始化:程序从`main()`函数启动,设置随机数种子并设定控制台编码为UTF-8。

   - 显示菜单:调用`menu()`函数显示游戏菜单供用户选择。

2. **初始化棋盘**

   - 输入选择:用户输入数字决定是否开始游戏。

   - 初始化棋盘状态:如果用户选择开始游戏,调用`Init(g_broad)`函数将全局变量`g_broad`(表示五子棋棋盘)所有位置初始化为空格(' ')。

3. **游戏循环**

   - 游戏开始后,进入主循环:

     a. 打印棋盘:首先调用`print(g_broad)`打印当前五子棋棋盘状态。

     b. 玩家落子:调用`playermove(g_broad)`获取玩家输入坐标,并在棋盘上放置棋子('x')。

     c. 检查游戏结束条件:调用`checkwinner(g_broad)`检查是否有玩家形成五子连线或棋盘是否已满。

       - 若有玩家获胜、电脑获胜或棋盘已满,则跳出循环。

     d. 电脑落子:若无胜者,调用`computermove(g_broad)`让电脑随机下棋('o'),此处AI策略仅为随机选择空位,非实际五子棋AI算法。

     e. 再次检查游戏结束条件:再次调用`checkwinner(g_broad)`。

4. **输出结果与结束游戏**

   - 根据`checkwinner()`返回的结果,在循环结束后判断并输出最终游戏结果:

     - 如果玩家胜(形成五子连线),则输出“玩家胜利!”及当前棋盘状态;

     - 如果电脑胜(形成五子连线),则输出“电脑胜利!”及当前棋盘状态;

     - 如果是平局(棋盘已满且无五子连线出现),则输出“和棋!”及当前棋盘状态;

     - 若未满足以上情况,则输出“游戏结束!goodbay~”。

整个流程通过一系列函数调用,实现了人机对弈的简化版五子棋游戏,涵盖了棋盘初始化、显示、玩家与电脑落子、以及五子连线检测等基本功能。但需要注意的是,这里的电脑落子策略非常简单,不是真正的五子棋AI算法。

本系统代码完整,经测试多组数据后,都能正常运行,现将部分功能截图如下

  

  

  

  

   

  

  

  

  

 

  

  

  

  

  

  

  

  

#include<stdio.h>
#include<stdlib.h>
#include<time.h>
#include<windows.h>//对应的代码在148行。如果运行结果中文出现乱码,请删除此行和148行代码。

#define ROW 5
#define COL 5

char g_broad[ROW][COL]; // 定义一个二维字符数组,用于存储棋盘状态
void menu(); // 声明菜单函数
void menu()
{
    printf(
"-----------------------\n");
    printf(
"------1.开始游戏-------\n");
    printf(
"------0.结束游戏-------\n");
    printf(
"-----------------------\n");
    printf(
"请输入您的选择:");
}

void Init(char broad[ROW][COL]) // 初始化棋盘
{
   
for (int row = 0; row < ROW; ++row)
    {
       
for (int col = 0; col < COL; ++col)
        {
            broad[row][col] =
' ';
        }
    }
}

void print(char broad[ROW][COL]) // 打印棋盘
{
   
for (int row = 0; row < ROW; ++row)
    {
        printf(
"| %c | %c | %c | %c | %c |\n", broad[row][0],
               broad[row][
1], broad[row][2], broad[row][3],
               broad[row][
4]);
       
if (row != ROW - 1)
        {
            printf(
" ---|---|---|---|--- \n");
        }
    }
}

void playermove(char broad[ROW][COL]) // 玩家落子
{
    printf(
"玩家落子:\n");
   
while (1)
    {
        printf(
"玩家请输入一组坐标:(row col)");
       
int row = 0;
       
int col = 0;
        scanf(
"%d %d", &row, &col);
       
if (row < 0 || row >= ROW || col < 0 || col >= COL)
        {
            printf(
"您输入的坐标非法,请重新输入:\n");
           
continue;
        }
       
else if (broad[row][col] != ' ')
        {
            printf(
"该位置已经被占用,请重新输入:\n");
           
continue;
        }
       
else
       
{
            broad[row][col] =
'x';
           
break;
        }
    }
}

void computermove(char broad[ROW][COL]) // 电脑落子
{
    printf(
"电脑落子:\n");
   
while (1)
    {
       
int row = rand() % ROW;
       
int col = rand() % COL;
       
if (broad[row][col] != ' ')
        {
           
continue;
        }
       
else
       
{
            broad[row][col] =
'o';
           
break;
        }
    }
}

int Isfull(char broad[ROW][COL]) // 判断棋盘是否已满
{
   
for (int row = 0; row < ROW; ++row)
    {
       
for (int col = 0; col < COL; ++col)
        {
           
if (broad[row][col] == ' ')
               
return 0;
        }
    }
   
return 1;
}

char checkwinner(char broad[ROW][COL]) // 检查获胜者
{
   
for (int row = 0; row < ROW; ++row)
    {
       
if (broad[row][0] == broad[row][1]
            && broad[row][
0] == broad[row][2]
            && broad[row][
0] == broad[row][3]
            && broad[row][
0] == broad[row][4]
            && broad[row][
0] != ' ')
        {
           
return broad[row][0];
        }
    }
   
for (int col = 0; col < COL; ++col)
    {
       
if (broad[0][col] == broad[1][col]
            && broad[
0][col] == broad[2][col]
            && broad[
0][col] == broad[3][col]
            && broad[
0][col] == broad[4][col]
            && broad[
0][col] != ' ')
        {
           
return broad[0][col];
        }
    }
   
if (broad[0][0] == broad[1][1]
        && broad[
0][0] == broad[2][2]
        && broad[
0][0] == broad[3][3]
        && broad[
0][0] == broad[4][4]
        && broad[
0][0] != ' ')
    {
       
return broad[0][0];
    }
   
if (broad[0][4] == broad[1][3]
        && broad[
0][4] == broad[2][2]
        && broad[
0][4] == broad[3][1]
        && broad[
0][4] == broad[4][0]
        && broad[
4][0] != ' ')
    {
       
return broad[4][0];
    }
   
if (Isfull(broad))
    {
       
return 'p';
    }
   
else
        return
' ';
}

int main()
{
    srand((
unsigned int)time(0)); // 设置随机数种子
   
SetConsoleOutputCP(CP_UTF8); // 设置控制台编码为UTF-8
   
int input = 0;
    menu();
//初始化棋盘,将棋盘初始化成' '
   
Init(g_broad);
    scanf(
"%d", &input);
   
char winner = ' ';
   
while (input)
    {
       
//第一次打印棋盘
       
print(g_broad);
       
//玩家输入,提示玩家输入一组坐标,检查游戏是否结束
       
playermove(g_broad);
        winner = checkwinner(g_broad);
       
if (winner != ' ')
        {
           
break;
        }
       
//电脑输入,瞎下,检查游戏是否结束
       
computermove(g_broad);
        winner = checkwinner(g_broad);
       
if (winner != ' ')
        {
           
break;
        }
    }
   
if (winner == 'x')
    {
        printf(
"玩家胜利!\n");
        print(g_broad);
    }
   
if (winner == 'o')
    {
        printf(
"电脑胜利!\n");
        print(g_broad);
    }
   
if (winner == 'p')
    {
        printf(
"和棋!\n");
        print(g_broad);
    }
   
if (winner == ' ')
    {
        printf(
"游戏结束!goodbay~\n");
       
return 0;
    }
   
return 0;
}

使用的时候,运行主函数(main)即可运行成功。

  • 21
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值