400字范文,内容丰富有趣,生活中的好帮手!
400字范文 > 简单的走迷宫小游戏(C语言编写 无指针 无链表)

简单的走迷宫小游戏(C语言编写 无指针 无链表)

时间:2020-12-23 09:44:15

相关推荐

简单的走迷宫小游戏(C语言编写 无指针 无链表)

目录

前言

代码编写思路

1.光标移动函数

2.地图

3.人物的移动(核心)

4.菜单、结束语句

5.附完整代码:

总结

优点:

缺点:

前言

笔者乃初学C语言,萌新一枚。深感C语言之博大,自叹所学之浅薄。今突发奇想,尝试用最简单之所学,编写了一款走迷宫小游戏。望各位大佬看后能在忍俊不禁之余,多多指教。

代码编写思路

1.光标移动函数

考虑到此程序运行过程中,需要不断在界面不同位置打印输出各种语句和字符,因此先通过编写自定义函数的方式,实现将光标移动至指定位置。调用时只需将光标所需移动位置的横竖坐标输入。

注:横坐标x从左向右,纵坐标y从上向下,初始值为(0,0)。如图所示:

由于笔者的操作系统是windows,因此为文件添加了“windows.h”的头文件,其中包含了其他的 Windows 头文件,这些头文件的部分也包含了其他头文件:

Windef.h 基本数据类型定义。 Winnt.h 支持 Unicode 的类型定义。 Winbase.h Kernel(内核)函数。 Winuser.h 用户界面函数。 Wingdi.h 图形设备接口函数。

具体代码如下:

void goto_xy(int x,int y) //移动光标到指定位置 {HANDLE hout;hout=GetStdHandle(STD_OUTPUT_HANDLE);COORD pos={x,y};SetConsoleCursorPosition(hout,pos);}

2.地图

定义一个静态全局二维数组map_way[20][20],其中我将用“0”代表通路,“1”代表墙壁,“2”代表陷阱,“3”代表终点。当调用自定义函数map时,将打印出地图。

代码如下(示例):

static int map_way[20][20]={{1,1,1,1,1,1,1,1,1,1},{0,0,0,1,0,0,0,0,0,1},{1,1,0,0,0,2,1,1,0,1},{1,0,0,1,1,1,1,0,0,1},{1,2,1,1,0,0,0,0,1,1},{1,0,0,0,0,1,0,1,0,3},{1,0,1,1,1,1,0,1,0,1},{1,0,1,0,0,0,2,1,0,1},{1,0,0,0,1,0,0,0,0,1},{1,1,1,1,1,1,1,1,1,1}};void map(){int i,j;goto_xy(0,0);for(i=0;i<10;i++){for(j=0;j<10;j++){if(map_way[i][j]==1)printf("▓");//墙壁 else if(map_way[i][j]==2)printf("※");//陷阱 else if(map_way[i][j]==3)printf("★");//终点 else printf("");//通路 }printf("\n");}}

调用函数效果如图所示:

3.人物的移动(核心)

定义两个全局变量man_x、man_y,分别代表当前人物所处坐标。这里我们需要对其初始化。因地图设计,入口位置为(0,1),所以初始化为man_x=0,man_y=1。当调用自定义函数move时,通过输入w、s、a、d,控制人物的上、下、左、右移动。当人物的坐标与之前定义的地图中各位置相重合时,执行不同的指令。

注:要考虑到字符的全角与半角,即像“▓”、“※”、“★”的这些字符,会占两个标准字符位置,故在调用光标移动函数及转义字符“\b”时,要考虑到

具体代码如下:

int man_x=0,man_y=1;int move() //为了能在运行过程中通过返回值的方式,提前退出当前函数,故将函数定义为了int型 {int i,j;char anjian;goto_xy(man_x,man_y);printf("☆");while(1){goto_xy(30,0); //指定位置读入 anjian=getchar();switch(anjian) //读入不同的字符,对应人物不同的移动方向 {case 'a':if(map_way[man_y][man_x-1]==1) //与墙壁相冲突 {goto_xy(30,5); printf("撞墙!"); //打印提示语句 break;}else if(map_way[man_y][man_x-1]==2) //掉入陷阱{goto_xy(30,4); printf("很遗憾,你掉入了陷阱!"); //打印提示语句 return 0; //退出 } else if(map_way[man_y][man_x-1]==3) //到达终点 {goto_xy(30,4);printf("恭喜你,成功通关!"); //打印提示语句 return 0; //退出 }else //将人物向指定位置移动 {goto_xy(man_x*2,man_y); //代表人物的字符☆占两个标准字符位置,应此要乘2 printf("\b\b☆"); //原因同上 man_x--;goto_xy(30,5);printf(""); //抹去之前打印的提示语句 break;}case 'd':if(map_way[man_y][man_x+1]==1){goto_xy(30,5); printf("撞墙!");break;}else if(map_way[man_y][man_x+1]==2){goto_xy(30,4); printf("很遗憾,你掉入了陷阱!"); return 0; } else if(map_way[man_y][man_x+1]==3){goto_xy(30,4);printf("恭喜你,成功通关!");return 0;}else {goto_xy(man_x*2,man_y);printf("");printf("☆"); man_x++;goto_xy(30,5);printf("");break;}case 'w':if(map_way[man_y-1][man_x]==1){goto_xy(30,5); printf("撞墙!");break;}else if(map_way[man_y-1][man_x]==2){goto_xy(30,4); printf("很遗憾,你掉入了陷阱!"); return 0; } else if(map_way[man_y-1][man_x]==3){goto_xy(30,4);printf("恭喜你,成功通关!");return 0;}else {goto_xy(man_x*2,man_y);printf(""); goto_xy(man_x*2,man_y-1);printf("☆");man_y--;goto_xy(30,5);printf("");break;}case 's':if(map_way[man_y+1][man_x]==1){goto_xy(30,5); printf("撞墙!");break;}else if(map_way[man_y+1][man_x]==2){goto_xy(30,4); printf("很遗憾,你掉入了陷阱!"); return 0; } else if(map_way[man_y+1][man_x]==3){goto_xy(30,4);printf("恭喜你,成功通关!");return 0;}else {goto_xy(man_x*2,man_y);printf(""); goto_xy(man_x*2,man_y+1);printf("☆");man_y++;goto_xy(30,5);printf("");break;}}}}

4.菜单、结束语句

编写菜单函数,调用时将打印出游戏名称、各符号所代表的含义、操作方法等等。

编写结束语句函数,在程序运行最后调用。

具体代码如下:

void menu(){goto_xy(0,12);printf("《迷宫》"); goto_xy(0,13);printf("上:w\t墙壁: \"▓\"\n下:s\t陷阱:\"※\"\n左:a\t终点:\"★\"\n右:d\t人物:\"☆\"\n(注:由于水平有限,每按一次移动按键都需按一下回车)");} void end(){goto_xy(30,5);printf("GAME OVER!");goto_xy(0,18);}

调用函数效果如图所示:

5.附完整代码:

#include<stdio.h>#include<windows.h>static int map_way[20][20]={{1,1,1,1,1,1,1,1,1,1},{0,0,0,1,0,0,0,0,0,1},{1,1,0,0,0,2,1,1,0,1},{1,0,0,1,1,1,1,0,0,1},{1,2,1,1,0,0,0,0,1,1},{1,0,0,0,0,1,0,1,0,3},{1,0,1,1,1,1,0,1,0,1},{1,0,1,0,0,0,2,1,0,1},{1,0,0,0,1,0,0,0,0,1},{1,1,1,1,1,1,1,1,1,1}};int man_x=0,man_y=1;void goto_xy(int x,int y) //移动光标到指定位置 {HANDLE hout;hout=GetStdHandle(STD_OUTPUT_HANDLE);COORD pos={x,y};SetConsoleCursorPosition(hout,pos);}void menu(){goto_xy(0,12);printf("《迷宫》"); goto_xy(0,13);printf("上:w\t墙壁: \"▓\"\n下:s\t陷阱:\"※\"\n左:a\t终点:\"★\"\n右:d\t人物:\"☆\"\n(注:由于水平有限,每按一次移动按键都需按一下回车)");} void end(){goto_xy(30,5);printf("GAME OVER!");goto_xy(0,18);} void map(){int i,j;goto_xy(0,0);for(i=0;i<10;i++){for(j=0;j<10;j++){if(map_way[i][j]==1)printf("▓");//墙壁 else if(map_way[i][j]==2)printf("※");//陷阱 else if(map_way[i][j]==3)printf("★");//终点 else //if(map_way[i][j]==0)printf("");//通路 }printf("\n");}}int move() //为了能在运行过程中通过返回值的方式,提前退出当前函数,故将函数定义为了int型 {int i,j;char anjian;goto_xy(man_x,man_y);printf("☆");while(1){goto_xy(30,0); //指定位置读入 anjian=getchar();switch(anjian) //读入不同的字符,对应人物不同的移动方向 {case 'a':if(map_way[man_y][man_x-1]==1) //与墙壁相冲突 {goto_xy(30,5); printf("撞墙!"); //打印提示语句 break;}else if(map_way[man_y][man_x-1]==2) //掉入陷阱{goto_xy(30,4); printf("很遗憾,你掉入了陷阱!"); //打印提示语句 return 0; //退出 } else if(map_way[man_y][man_x-1]==3) //到达终点 {goto_xy(30,4);printf("恭喜你,成功通关!"); //打印提示语句 return 0; //退出 }else //将人物向指定位置移动 {goto_xy(man_x*2,man_y); //代表人物的字符☆占两个标准字符位置,应此要乘2 printf("\b\b☆"); //原因同上 man_x--;goto_xy(30,5);printf(""); //抹去之前打印的提示语句 break;}case 'd':if(map_way[man_y][man_x+1]==1){goto_xy(30,5); printf("撞墙!");break;}else if(map_way[man_y][man_x+1]==2){goto_xy(30,4); printf("很遗憾,你掉入了陷阱!"); return 0; } else if(map_way[man_y][man_x+1]==3){goto_xy(30,4);printf("恭喜你,成功通关!");return 0;}else {goto_xy(man_x*2,man_y);printf("");printf("☆"); man_x++;goto_xy(30,5);printf("");break;}case 'w':if(map_way[man_y-1][man_x]==1){goto_xy(30,5); printf("撞墙!");break;}else if(map_way[man_y-1][man_x]==2){goto_xy(30,4); printf("很遗憾,你掉入了陷阱!"); return 0; } else if(map_way[man_y-1][man_x]==3){goto_xy(30,4);printf("恭喜你,成功通关!");return 0;}else {goto_xy(man_x*2,man_y);printf(""); goto_xy(man_x*2,man_y-1);printf("☆");man_y--;goto_xy(30,5);printf("");break;}case 's':if(map_way[man_y+1][man_x]==1){goto_xy(30,5); printf("撞墙!");break;}else if(map_way[man_y+1][man_x]==2){goto_xy(30,4); printf("很遗憾,你掉入了陷阱!"); return 0; } else if(map_way[man_y+1][man_x]==3){goto_xy(30,4);printf("恭喜你,成功通关!");return 0;}else {goto_xy(man_x*2,man_y);printf(""); goto_xy(man_x*2,man_y+1);printf("☆");man_y++;goto_xy(30,5);printf("");break;}}}} int main(){menu(); map();move();end();system("pause");//若要生成可执行文件,加上此句可确保不会闪退 return 0;}

运行效果图:

总结

优点:

1.地图搭建较为容易。只需改变定义的二维数组map_way,即可改变地图。(但需考虑到菜单等界面布局,不然只增大地图易导致部分输出内容重叠,产生未知错误)

2.采用数字代替特殊字符的方式,降低编写难度,增强代码的可读性。

3.涉及到的知识简单易懂,除了自定义的光标移动函数外,并未涉及到诸如指针、链表、文件等较为深奥的东西。(笔者在为自己的菜找借口)

缺点:

1.未能实现地图的随机生成,搭建地图的方式僵硬呆板。若要搭建更大的地图,例如40×40的地图,则需初始化总计1600个数字,工作量无疑是巨大的。

2.在输入控制人物移动的字符时,仍需输入一个字符按一下enter键,无疑影响游戏体验。

3.游戏界面只是基本的字符,没有复杂美观的图案,看起来单调乏味。

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。