『推箱子』苏晓辉の转专业面试作品 · 纪念品

其实Day61就写好了,审核大大为什么没给过呢,是因为前面的偷猎者系统和自解压包嘛

 

我明天面试要用了啊不要搞我啊呜呜呜

#include <iostream>
#include<stdio.h>
#include<conio.h>//键盘控制头函数!!!!!!! 
int T             ;//按键检测  (大写) ·····ASD+W 
int now=72        ;//现在的地点(玩家) ·····坐标 7行2列 (88棋盘内部) 
int nex=2745409660;//下一个地点(状态研判) ···状态 
int w=10        ;//地图宽度(数表数据端口) ···数表长度 
int m[100]={//地图参数 
1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,0,0,0,1,
1,0,3,3,3,0,0,0,0,1,
1,0,0,1,0,0,0,0,0,1,
1,0,0,0,0,0,4,0,0,1,
1,0,4,0,0,0,0,0,0,1,
1,0,0,0,0,1,1,0,0,1,
1,0,2,0,0,0,0,0,0,1,
1,0,0,0,0,0,4,0,0,1,
1,1,1,1,1,1,1,1,1,1};
//--------游戏结束判定函数--------------------------------------
int Over(int sum){
	int n=0;//sum有几个可归位点,是否全部填满 
	for(int i=0;i<100;i++)			
		if(m[i]==6) n++;
	if(sum==n){	printf("恭喜通关!!!\n预祝苏晓辉同学转专业成功~\n\n");
	     return 1; }
	else return 0;}
//--------推动判定函数--------------------------------------
int PD(int a,int s){//1234上下左右   可以推动:再点不能是·箱子/墙壁/已归位点 
     if(a==1&&m[s-2*w]!=1&&m[s-2*w]!=3&&m[s-2*w]!=6) return 666; //上 
else if(a==2&&m[s+2*w]!=1&&m[s+2*w]!=3&&m[s+2*w]!=6) return 666; //下 
else if(a==3&&m[s-2]!=1    &&m[s-2]!=3  &&m[s-2]!=6) return 666; //左 
else if(a==4&&m[s+2]!=1    &&m[s+2]!=3  &&m[s+2]!=6) return 666;///右 
	 else       return 233;} 
//----主循环(显示模块·中断判定/推动判定模块·读取模块·变化模拟模块)---------------------------
int main()
{	while(1){//printf("\n\n\n\n\n\n\n\n\n"); 
//--------------显示模块------------------------------------------------- 
		system("cls");//刷新页面,防止刷屏!!!!!!!!!!!!! 
		for(int x=0;x<100;x++){//地图显示机制 
			switch(m[x]){
				case 0:printf("  ");break;    //空地 
				case 1:printf("□");break;    //墙体 
				case 2:printf("HU");break;    //人·Human
				case 3:printf("■");break;    //箱子  
				case 4:printf("De");break;    //目的地·Destination 
				case 5:printf("×");break;    //人·目的地·重合 
				case 6:printf("√");break;    //箱·目的地·重合 
			}if(x%w==9) printf("\n");		//换行判断 
		}
//--------游戏终止判断/按键读取模块----------------------------------------------
		if(Over(3))break;//游戏结束判断 返回1中断 
		T=_getch();//按键实时读取!!不可采用scanf!!
	//保存为int形式,采用ASCII判断按键,单引号字符表达亦可 
//------按键执行判断模块-----------------------------------------------------------------------
		if(T=='W'){//往上走
			nex=m[now-w];//下点·状态侦查 
			if(nex==0||nex==4){		//T1下点·空地/目标 	
				if(nex==0)   m[now-w]=2;//A下点·空地·必须变人 
				if(nex==4)	 m[now-w]=5;//B下点·目标·必须变重合人
				if(m[now]==5)m[now]=4; 	//A这点·重合人·必须变目标		
				if(m[now]==2)m[now]=0;  //B这点·人·必须变空地
				now-=w;} 
			else if((nex==6||nex==3)&&(PD(1,now)==666)){//T2下点·箱子已归位·可推动 
				if(nex==6)			m[now-w]=5;//下点·已归位点·必须变人重合 
				if(nex==3)			m[now-w]=2;//下点·箱子·必须变人 
				if(m[now-2*w]==0)	m[now-2*w]=3;//再点·空地·必须变箱子 
				if(m[now-2*w]==4)	m[now-2*w]=6;//再点·目标点·必须变已归位点 
				if(m[now]==2)	    m[now]=0;	//此点·人·必须变空地 
				if(m[now]==5)    	m[now]=4; 	//此点·人重合·必须变目标点 
				now-=w;}
		}//W全体系完成    玩家位移只能在判定可以移动时候才可产生偏移 
//---------S向下-----------------------------------------------------------------------
		else if(T=='S'){//往下走
			nex=m[now+w];//下点·状态侦查 
			if(nex==0||nex==4){		//T1下点·空地/目标 	
				if(nex==0)   m[now+w]=2;//A下点·空地·必须变人 
				if(nex==4)	 m[now+w]=5;//B下点·目标·必须变重合人
				if(m[now]==5)m[now]=4; 	//A这点·重合人·必须变目标		
				if(m[now]==2)m[now]=0;  //B这点·人·必须变空地
				now+=w;} 
			else if((nex==6||nex==3)&&(PD(2,now)==666)){//T2下点·箱子/已归位·且可推动 
				if(nex==6)			m[now+w]=5;//下点·已归位点·必须变人重合 
				if(nex==3)			m[now+w]=2;//下点·箱子·必须变人 
				if(m[now+2*w]==0)	m[now+2*w]=3;//再点·空地·必须变箱子 
				if(m[now+2*w]==4)	m[now+2*w]=6;//再点·目标点·必须变已归位点 
				if(m[now]==2)	    m[now]=0;	//此点·人·必须变空地 
				if(m[now]==5)    	m[now]=4; 	//此点·人重合·必须变目标点 
				now+=w;}
		}//S全体系完成
//-------------向左----------------------------------------------------------------
		else if(T=='A'){//往左走
			nex=m[now-1];//下点·状态侦查 
			if(nex==0||nex==4){		//T1下点·空地/目标 	
				if(nex==0)   m[now-1]=2;//A下点·空地·必须变人 
				if(nex==4)	 m[now-1]=5;//B下点·目标·必须变重合人
				if(m[now]==5)m[now]=4; 	//A这点·重合人·必须变目标		
				if(m[now]==2)m[now]=0;  //B这点·人·必须变空地
				now-=1;} 
			else if((nex==6||nex==3)&&(PD(3,now)==666)){//T2下点·箱子·且可推动 
				if(nex==6)			m[now-1]=5;//下点·已归位点·必须变人重合 
				if(nex==3)			m[now-1]=2;//下点·箱子·必须变人 
				if(m[now-2]==0)		m[now-2]=3;	//再点·空地·必须变箱子 
				if(m[now-2]==4)		m[now-2]=6;	//再点·目标点·必须变已归位点 
				if(m[now]==2)	    m[now]=0;	//此点·人·必须变空地 
				if(m[now]==5)    	m[now]=4; 	//此点·人重合·必须变目标点 
				now-=1;}
		}//A全体系完成
//---------往右--------------------------------------------------------------------
		else if(T=='D'){//往右边走
			nex=m[now+1];//下点·状态侦查 
			if(nex==0||nex==4){		//T1下点·空地/目标 	
				if(nex==0)   m[now+1]=2;//A下点·空地·必须变人 
				if(nex==4)	 m[now+1]=5;//B下点·目标·必须变重合人
				if(m[now]==5)m[now]=4; 	//A这点·重合人·必须变目标		
				if(m[now]==2)m[now]=0;  //B这点·人·必须变空地
				now+=1;} 
			else if((nex==6||nex==3)&&(PD(4,now)==666)){//T2下点·箱子·且可推动 
				if(nex==6)			m[now+1]=5;//下点·已归位点·必须变人重合 
				if(nex==3)			m[now+1]=2;//下点·箱子·必须变人 
				if(m[now+2]==0)		m[now+2]=3;	//再点·空地·必须变箱子 
				if(m[now+2]==4)		m[now+2]=6;	//再点·目标点·必须变已归位点 
				if(m[now]==2)	    m[now]=0;	//此点·人·必须变空地 
				if(m[now]==5)    	m[now]=4; 	//此点·人重合·必须变目标点 
				now+=1;}
		}//A全体系完成
	}system("pause");return 0;
}

推到墙角了,救不了了,毁灭吧

watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzIxODkzMTYz,size_16,color_FFFFFF,t_70

转专业,想去计科,竞争好激烈,47进13,需要干掉70%的竞争对手

于是晓辉同学想起了静语学长翔哥的话:要做一个作品!!给老师看!!

竞争嘛,不磕碜

可是只有两周时间了,我想起了同学以前的扫雷游戏

研究了一会发现需要控制随机数,鼠标控制,还有大范围展开的判断

(点一下打开好多空区域的那个)笑死,根本来不及

晓辉还是想着C++写个游戏,不过还是没有头绪

于是去翻以前的存货,发现了 键盘记录器C++实现

(小时候很喜欢黑客,觉得很酷,所以由研究各种花里胡哨的东西)

这让我联想到键盘控制读取我已经可以实现了

想C++小游戏,突发奇想电视机顶盒小时候的游戏《推箱子》/俄罗斯方块

后者被否决了,前者可以用矩阵控制,按一下显示一个,感觉可以实现

用遥控器控制,穿越地形,达成你的目标

同样的原理还计划开发《2048》,不过这个多了一个随机数的产生

也是按一下出来一个图形;不过算法不太好搞,已经主框架搭建好了

不知道在面试前能不能开发出来

对于两个小游戏的制作,启动突击计划 代号·惊鸿(没改小时候中二的品性)

时间 鸿蒙纪元☆龙渊Day52-Day63 共历时  11天 完成推箱子游戏最后优化工作

Day63  2021/06/29下午要机考了我还在写这个CSDN

接下来是我的研究进度的回溯

1.全局部署

        采用10*10棋盘,二维数组;后来发现二维很难控制,于是切换成一维

        10*10还需要控制边界,变成11*11会让一维数组很难看

        时间紧迫,只好缩小成8*8,地图依旧采用10*10的一维数组

2.基本规则  不可以推动两个箱子/不可以穿墙(后来出bug修了半天发现就差一个箱子条件)

        推进坑里的可以再推出来

3.地图基本单元研判

        空地  代号0        墙体  代号1        玩家  代号2

        箱子  代号3        目标  代号4        人重  代号5

        箱重  代号6

                此点:当前玩家站立点

                下点:玩家下一步走到的点 

                再点:玩家下两步走到的点(判断是否撞墙)

箱重:箱子再目标点上,已经归位,离开后还原为5(人进去推走了)

人重:人站在目标点上,人离开后还原为4

目标:箱子进去变6,人进去变5

箱子:被推走了,此点变成2

玩家:溜了溜了,此点变成0

空地:来箱子变3,来人变2

4.基本推动情况分析

        A.人与空地        可以保证下一步一定能进去

                此点        人有两种情况:人2/人重5

                下点        空地两种情况:空地0/目标点4

        所以这种2*2=4种情况

        B.人与箱子        箱子不一定推得动,需要判断

                此点        人有两种情况:人2/人重5

                下点        箱子两种情况:箱3/归位6

                再点        空地两种情况:空地0/目标点4

        所以2*2*2=8中情况 总共12种情况

5.于是我陷入了困顿,不会要写12个判断吧

我想了想可以拆上边两大类,进行再判断

我研究了一天多,发现重点在于下点 · 状态:箱子还是空地

但是还没有头绪,所以先制定了宏观框架

6.宏观框架:地图显示模块--键盘读取模块--结束条件判定模块--按键处置模块

        附加函数:推动判断模块

        按键处置模块:ASDW四种方案,总体思路一样,改一下数据变化方向就好

        所以我决定先主攻W向上的方向

地图显示:一维数组打表+回车判断

键盘读取:conio.h键盘钩子+T=_getch();读取为int(本来想搞ASCII的后来发现单引号也行)

结束条件:看看几个目标点是否都进入6状态,是则胜利!!

按键处置:分ASDW+12种基本状态处理;数据结构方面

        上下则±W(数组总宽度)来调整玩家位置,同时确定三个基本点位置(此下再)

推动判断:看再点,不可以是墙体/箱子/归位点

7.按键处置模块 · 判断机制 · 攻关  8种情况

        最终方案在宏观框架制定完成后有了头绪 · 诶很开心买了个大雪碧吃  

watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzIxODkzMTYz,size_16,color_FFFFFF,t_70

这写的什么玩意儿,然后重写了一张,草稿纸没带只好牺牲一下蓝皮本了呜呜赵老师dbq

watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzIxODkzMTYz,size_16,color_FFFFFF,t_70

下点拆成4类:空地/目标点       箱子/已归位

写完代码,240多行,发现前后两类(空地/箱子)代码可以合并,有很多重复点,4类变2类

优化完差不多130行,少了一半多

        判断机制如下  优化后可以完美覆盖12种情况

                人--空地(如果:下点是空位/DE点)

                        下点·O空位                    变成玩家

                        下点·DE目标点              变成人重合

                        此点·HU玩家                  变成空位

                        此点·X人重合                  变成目标点DE

                人--箱子(如果:下点是箱子/归位点  且  可以推得动)

                        下点·箱子                变成人

                        下点·归位点            变成人重合

                        再点·空地                变成箱子

                        再点·DE点               变成归位点

                        此点·玩家                 变成空位

                        此点·人重合             变成DE点

(我当时漏了是不是箱子判断导致穿墙,我会在末尾放上这个错误代码)

8.数据结构运用:上下采用±w,左右采用±1,稍微改一改就好

        此处W是 地图列表一行的总宽度

9.显示模块:cls刷新+打表,防止刷屏

读取模块:来键盘钩子,保存为ASCII int形式,也可以采用'  '来调用

---------------------------------------------------------------------------------------------------------

调试比较辛苦,已经很长时间没有碰算法和数据结构了

这次转专业算是把我逼上梁山吧,不过做的很仓促

我希望能展现我的能力和学习的兴趣、信心,能够经得起考验

我要转计科!!!俺会不懈努力的~

--------------------------------------------------------------------------------------------------------

下面是穿墙的错误代码,只是缺少了下点是否是箱子的判断

#include <iostream>
#include<stdio.h>
#include<conio.h>//键盘控制头函数!!!!!!! 
int T             ;//按键检测  (大写) ·····ASD+W 
int now=72        ;//现在的地点(玩家) ·····坐标 7行2列 (88棋盘内部) 
int nex=2745409660;//下一个地点(状态研判) ···状态 
int w=10        ;//地图宽度(数表数据端口) ···数表长度 
int m[100]={//地图参数 
1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,0,0,0,1,
1,0,3,3,3,0,0,0,0,1,
1,0,0,1,0,0,0,0,0,1,
1,0,0,0,0,0,4,0,0,1,
1,0,4,0,0,0,0,0,0,1,
1,0,0,0,0,1,1,0,0,1,
1,0,2,0,0,0,0,0,0,1,
1,0,0,0,0,0,4,0,0,1,
1,1,1,1,1,1,1,1,1,1};
//--------游戏结束判定函数--------------------------------------
int Over(int sum){
	int n=0;//sum有几个可归位点,是否全部填满 
	for(int i=0;i<100;i++)			
		if(m[i]==6) n++;
	if(sum==n){	printf("恭喜通关!!!\n预祝苏晓辉同学转专业成功~\n\n");
	     return 1; }
	else return 0;}
//--------推动判定函数--------------------------------------
int PD(int a,int s){//1234上下左右   可以推动:再点不能是·箱子/墙壁/已归位点 
     if(a==1&&m[s-2*w]!=1&&m[s-2*w]!=3&&m[s-2*w]!=6) return 666; //上 
else if(a==2&&m[s+2*w]!=1&&m[s+2*w]!=3&&m[s+2*w]!=6) return 666; //下 
else if(a==3&&m[s-2]!=1    &&m[s-2]!=3    &&m[s-2]!=6)	 return 666; //左 
else if(a==4&&m[s+2]!=1    &&m[s+2]!=3    &&m[s+2]!=6) 	 return 666;///右 
	 else       return 233;} 
//----主循环(显示模块·中断判定/推动判定模块·读取模块·变化模拟模块)---------------------------
int main()
{	while(1){//printf("\n\n\n\n\n\n\n\n\n"); 
//--------------显示模块------------------------------------------------- 
		system("cls");//刷新页面,防止刷屏!!!!!!!!!!!!! 
		for(int x=0;x<100;x++){//地图显示机制 
			switch(m[x]){
				case 0:printf("  ");break;    //空地 
				case 1:printf("□");break;    //墙体 
				case 2:printf("HU");break;    //人·Human
				case 3:printf("■");break;    //箱子  
				case 4:printf("De");break;    //目的地·Destination 
				case 5:printf("×");break;    //人·目的地·重合 
				case 6:printf("√");break;    //箱·目的地·重合 
			}if(x%w==9) printf("\n");		//换行判断 
		}
//--------游戏终止判断/按键读取模块----------------------------------------------
		if(Over(3))break;//游戏结束判断 返回1中断 
		T=_getch();//按键实时读取!!不可采用scanf!!
	//保存为int形式,采用ASCII判断按键,单引号字符表达亦可 
//------按键执行判断模块-----------------------------------------------------------------------
		if(T=='W'){//往上走
			nex=m[now-w];//下点·状态侦查 
			if(nex==0||nex==4){		//T1下点·空地/目标 	
				if(nex==0)   m[now-w]=2;//A下点·空地·必须变人 
				if(nex==4)	 m[now-w]=5;//B下点·目标·必须变重合人
				if(m[now]==5)m[now]=4; 	//A这点·重合人·必须变目标		
				if(m[now]==2)m[now]=0;  //B这点·人·必须变空地
				now-=w;} 
			else if(PD(1,now)==666){//T2下点·可推动 
				if(nex==6)			m[now-w]=5;//下点·已归位点·必须变人重合 
				if(nex==3)			m[now-w]=2;//下点·箱子·必须变人 
				if(m[now-2*w]==0)	m[now-2*w]=3;//再点·空地·必须变箱子 
				if(m[now-2*w]==4)	m[now-2*w]=6;//再点·目标点·必须变已归位点 
				if(m[now]==2)	    m[now]=0;	//此点·人·必须变空地 
				if(m[now]==5)    	m[now]=4; 	//此点·人重合·必须变目标点 
				now-=w;}
		}//W全体系完成    玩家位移只能在判定可以移动时候才可产生偏移 
//---------S向下-----------------------------------------------------------------------
		else if(T=='S'){//往下走
			nex=m[now+w];//下点·状态侦查 
			if(nex==0||nex==4){		//T1下点·空地/目标 	
				if(nex==0)   m[now+w]=2;//A下点·空地·必须变人 
				if(nex==4)	 m[now+w]=5;//B下点·目标·必须变重合人
				if(m[now]==5)m[now]=4; 	//A这点·重合人·必须变目标		
				if(m[now]==2)m[now]=0;  //B这点·人·必须变空地
				now+=w;}  
			else if(PD(2,now)==666){//T2下点·可推动 
				if(nex==6)			m[now+w]=5;//下点·已归位点·必须变人重合 
				if(nex==3)			m[now+w]=2;//下点·箱子·必须变人 
				if(m[now+2*w]==0)	m[now+2*w]=3;//再点·空地·必须变箱子 
				if(m[now+2*w]==4)	m[now+2*w]=6;//再点·目标点·必须变已归位点 
				if(m[now]==2)		m[now]=0;	//此点·人·必须变空地 
				if(m[now]==5)		m[now]=4; 	//此点·人重合·必须变目标点 
				now+=w;}//玩家位移 
		}//S全体系完成 
//-------------向左----------------------------------------------------------------
		else if(T=='A'){//往左走
			nex=m[now-1];//下点·状态侦查 
			if(nex==0||nex==4){		//T1下点·空地/目标 	
				if(nex==0)   m[now-1]=2;//A下点·空地·必须变人 
				if(nex==4)	 m[now-1]=5;//B下点·目标·必须变重合人
				if(m[now]==5)m[now]=4; 	//A这点·重合人·必须变目标		
				if(m[now]==2)m[now]=0; //B这点·人·必须变空地 
				now-=1;}
			else if(PD(3,now)==666){//T2下点·可推动 
				if(nex==6)			m[now-1]=5;//下点·已归位点·必须变人重合 
				if(nex==3)			m[now-1]=2;//下点·箱子·必须变人 
				if(m[now+2*w]==0)	m[now-2]=3;//再点·空地·必须变箱子 
				if(m[now+2*w]==4)	m[now-2]=6;//再点·目标点·必须变已归位点 
				if(m[now]==2)		m[now]=0;	//此点·人·必须变空地 
				if(m[now]==5)		m[now]=4; 	//此点·人重合·必须变目标点 
				now-=1;}//玩家位移 
		}//A全体系完成 
//---------往右--------------------------------------------------------------------
		else if(T=='D'){//往左走
			nex=m[now+1];//下点·状态侦查 
			if(nex==0||nex==4){		//T1下点·空地/目标 	
				if(nex==0)   m[now+1]=2;//A下点·空地·必须变人 
				if(nex==4)	 m[now+1]=5;//B下点·目标·必须变重合人
				if(m[now]==5)m[now]=4; 	//A这点·重合人·必须变目标		
				if(m[now]==2)m[now]=0;  //B这点·人·必须变空地
				now+=1;} 
			else if(PD(4,now)==666){//T2下点·可推动 
				if(nex==6)			m[now+1]=5;//下点·已归位点·必须变人重合 
				if(nex==3)			m[now+1]=2;//下点·箱子·必须变人 
				if(m[now+2*w]==0)	m[now+2]=3;//再点·空地·必须变箱子 
				if(m[now+2*w]==4)	m[now+2]=6;//再点·目标点·必须变已归位点 
				if(m[now]==2)		m[now]=0;	//此点·人·必须变空地 
				if(m[now]==5)		m[now]=4; 	//此点·人重合·必须变目标点 
				now+=1;
				}//玩家位移 
		}//D全体系完成 
	}system("pause");return 0;
}

毁灭吧,我累了

watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzIxODkzMTYz,size_16,color_FFFFFF,t_70

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

影月丶暮风

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值