C语言学习笔记第五天_项目训练
-
添加自定义的一个函数库文件 <getch.h>
步骤:
-
1、在windows中把getch.h放入共享文件夹(文件我放在文末,自取)
-
2、在Ubuntu终端输入cd /media/sf_Share/ 进入共享文件夹
-
3、复制getch.h到C标准库中
sudo cp getch.h /usr/include/
-
4、加读权限
sudo chmod +r /usr/include/getch.h
-
5、导入getch.h头文件,使用getch()函数获取键值
Ubuntu下的键值:
上:183 下:184 左:186 右:185
-
-
项目一:走迷宫
数据分析: 1、定义二维字符数组作为迷宫地图 2、定义变量记录角色的位置 x y 3、时间:time(NULL) 获取1970-1-1到运行时过了总秒数 逻辑分析: 进入死循环: 1、显示地图 2、判断是否到达出口 如果是:程序结束 3、获取方向键并处理 判断前方是不是路' ' 如果是: 1、把旧位置变成' ' 2、把新位置变成'@' 3、更新角色位置坐标 x y
个人代码实现:
#include <stdio.h> #include <time.h> #include <stdlib.h> #include <stdint.h> #include <getch.h> int main(int argc,const char* argv[]) { const uint8_t MAP_SIZE=10; int8_t loc_x=0,loc_y=0; char arr[10][10]={ {'$','*','*','*','*','*','*','*','*','*'}, {' ',' ',' ','*','*',' ',' ',' ',' ','*'}, {'*',' ','*','*','*',' ','*','*',' ','*'}, {'*',' ','*',' ',' ',' ','*','*',' ','*'}, {'*',' ','*','*','*',' ','*','*',' ',' '}, {'*',' ','*','*','*',' ','*','*',' ','*'}, {'*',' ',' ',' ',' ',' ','*','*',' ','*'}, {'*',' ',' ','*','*','*','*','*',' ','*'}, {'*','*','*','*',' ',' ','*','*','*','*'}, {'*','*','*','*','*','*','*','*','*','*'}, }; time_t time_start; time_start = time(NULL); for(;;) { //清理屏幕 system("clear"); for(int i=0;i<10;i++) { for(int j=0;j<10;j++) { printf("%c ",arr[i][j]); } printf("\n"); } //判断是否游戏结束 if(loc_x==4&&loc_y==9) { printf("游戏结束……\n"); break; } int ch=getch(); int new_loc_x=loc_x,new_loc_y=loc_y; //根据读取键盘值判断走向 switch(ch) { case 183:new_loc_x-=1;break; case 184:new_loc_x+=1;break; case 185:new_loc_y+=1;break; case 186:new_loc_y-=1;break; default:break; } //刷新位置参数 if(arr[new_loc_x][new_loc_y]==' ') { arr[loc_x][loc_y]=' '; loc_x=new_loc_x; loc_y=new_loc_y; arr[loc_x][loc_y]='$'; } } time_t time_end; time_end = time(NULL); printf("您花费的时间为:%lus\n",time_end-time_start); return 0; }
-
项目二:推箱子
数据分析:
1、确定数值与字符的对应关系0 ' ' 1 '@' 2 ' # ' 3 ' $ ' 4 ' O ' 5 ' @ ' 7 ' $ '
2、定义8*8整数地图并初始化
3、定义记录角色位置的变量 x y
4、定义记录步数的变量逻辑分析: 进入死循环 1、清理屏幕、显示地图 `if(0 == map[i][j]) printf(" ");` 2、判断是否游戏胜利 3、获取方向键并处理 1、前方是路/目标点,参考走迷宫 前方 +1 原位置 -1 更新坐标 2、前方是箱子 箱子的前方是路\目标点 人前方的前方 +3 人前方 -3+1 人原位置 -1 更新左边
个人代码实现:
按照目前进度,没有学过#define 数组 结构体 联合等相关内容,故代码
有点非常粗糙
#include <stdio.h>
#include <stdint.h>
#include <getch.h>
#include <stdlib.h>
int main(int argc,const char* argv[])
{
uint8_t map[8][8]={
{0,0,2,2,2,2,0,0},
{0,0,2,4,4,2,0,0},
{0,2,2,0,4,2,2,0},
{0,2,0,0,3,4,2,0},
{2,2,0,3,0,0,2,2},
{2,0,0,2,3,3,0,2},
{2,0,0,1,0,0,0,2},
{2,2,2,2,2,2,2,2},
};
int step=0;
int loc_x=6,loc_y=3;
char sign[8]={' ','@','*','#','&','@','1','!'};
// 0路径
// 1人
// 2墙壁
// 3箱子
// 4目标
// 5目标和人在一起
// 6
// 7目标和箱子在一起
//打印地图
for(;;)
{
system("clear");
int cnt=0;
for(int i=0;i<8;i++)
{
for(int j=0;j<8;j++)
{
if(map[i][j]==7)
{
cnt+=1;
}
printf("%c ",sign[map[i][j]]);
}
printf("\n");
}
if(cnt==4)
{
printf("游戏结束……您走了%d步",step);
}
int ch=getch();
int new_loc_x=loc_x,new_loc_y=loc_y;
switch(ch)
{
case 183:new_loc_x-=1;break;
case 184:new_loc_x+=1;break;
case 185:new_loc_y+=1;break;
case 186:new_loc_y-=1;break;
}
if(map[new_loc_x][new_loc_y] == 0)//前面是路
{
map[loc_x][loc_y]-=1;
loc_x = new_loc_x;
loc_y = new_loc_y;
map[loc_x][loc_y] +=1;
step+=1;
}
if(map[new_loc_x][new_loc_y] == 4 )//前面是目标
{
map[loc_x][loc_y]-=1;
loc_x = new_loc_x;
loc_y = new_loc_y;
map[loc_x][loc_y] +=1;
step +=1;
}
if(ch==183
&&( map[new_loc_x][new_loc_y]==3|| map[new_loc_x][new_loc_y]==7)
&& (map[new_loc_x-1][new_loc_y]==0 || map[new_loc_x-1][new_loc_y]==4))
{
map[new_loc_x-1][new_loc_y]+=3;
map[new_loc_x][new_loc_y] -= 2;
map[loc_x][loc_y]-=1;
loc_x = new_loc_x;
loc_y = new_loc_y;
step+=1;
}
if(ch==184
&& (map[new_loc_x][new_loc_y]==3 || map[new_loc_x][new_loc_y]==7)
&&(map[new_loc_x+1][new_loc_y]==0 || map[new_loc_x+1][new_loc_y]==4))
{
map[new_loc_x+1][new_loc_y]+=3;
map[new_loc_x][new_loc_y] -=2;
map[loc_x][loc_y]-=1;
loc_x = new_loc_x;
loc_y = new_loc_y;
step+=1;
}
if(ch==185
&&( map[new_loc_x][new_loc_y]==3 || map[new_loc_x][new_loc_y]==7)
&&(map[new_loc_x][new_loc_y+1]==0 || map[new_loc_x][new_loc_y+1]==4))
{
map[new_loc_x][new_loc_y+1]+=3;
map[new_loc_x][new_loc_y] -=2;
map[loc_x][loc_y]-=1;
loc_x = new_loc_x;
loc_y = new_loc_y;
step+=1;
}
if(ch==186
&& (map[new_loc_x][new_loc_y]==3 || map[new_loc_x][new_loc_y]==7)
&&(map[new_loc_x][new_loc_y-1]==0 || map[new_loc_x][new_loc_y-1]==4))
{
map[new_loc_x][new_loc_y-1]+=3;
map[new_loc_x][new_loc_y] -=2;
map[loc_x][loc_y]-=1;
loc_x = new_loc_x;
loc_y = new_loc_y;
step+=1;
}
}
return 0;
}
<getch.h>文件如下:
#ifndef GETCH_H
#define GETCH_H
#include <termios.h>
#include <unistd.h>
#include <stdio.h>
// 修改终端的控制方式,1取消回显、确认 2获取数据 3还原
static int getch(void)
{
// 记录终端的配置信息
struct termios old;
// 获取终端的配置信息
tcgetattr(STDIN_FILENO,&old);
// 设置新的终端配置
struct termios new = old;
// 取消确认、回显
new.c_lflag &= ~(ICANON|ECHO);
// 设置终端配置信息
tcsetattr(STDIN_FILENO,TCSANOW,&new);
// 在新模式下获取数据
int key_val = 0;
do{
key_val += getchar();
}while(stdin->_IO_read_end - stdin->_IO_read_ptr);
// 还原配置信息
tcsetattr(STDIN_FILENO,TCSANOW,&old);
return key_val;
}
#endif//GETCH_H
最后,如有更好思路或着看出bug的,还请不吝赐教,谢谢……