POJ 3083 Children of the Candy Corn DFS及BFS搜索

本文介绍了一种使用BFS和模拟的方法解决迷宫寻路问题,包括向左和向右的移动策略,通过递归的方式尝试到达终点,并给出了两种不同的实现方案。

///这题不是很理解有待于重做,BFS+模拟,模拟有点麻烦 #include<stdio.h> #include<string.h> #include<queue> using namespace std; queue<int> q; int w,h; char map[45][45]; int dl[4][2]={{0,-1},{-1,0},{0,1},{1,0}}; int vis[45][45]; int dire,k;///指向当前移动方向。 int left(int a,int b,int c,int d) { if(a==c&&b==d) return 0; int t=(dire-1+4)%4; if(map[a+dl[t][0]][b+dl[t][1]]!='#') { k++; a=a+dl[t][0];b=b+dl[t][1]; dire=t; left(a,b,c,d); } else { if(map[a+dl[dire][0]][b+dl[dire][1]]!='#') { k++; a=a+dl[dire][0]; b=b+dl[dire][1]; left(a,b,c,d); } else { dire=(dire+1)%4; if(map[a+dl[dire][0]][b+dl[dire][1]]!='#') { k++; a=a+dl[dire][0]; b=b+dl[dire][1]; left(a,b,c,d); } else { dire=(dire+1)%4; k++; a=a+dl[dire][0]; b=b+dl[dire][1]; left(a,b,c,d); } } } return 0; } int right(int a,int b,int c,int d) { if(a==c&&b==d) return 0; int t=(dire+1)%4; if(map[a+dl[t][0]][b+dl[t][1]]!='#') { k++; a=a+dl[t][0];b=b+dl[t][1]; dire=t; right(a,b,c,d); } else { if(map[a+dl[dire][0]][b+dl[dire][1]]!='#') { k++; a=a+dl[dire][0]; b=b+dl[dire][1]; right(a,b,c,d); } else { dire=(dire-1+4)%4; if(map[a+dl[dire][0]][b+dl[dire][1]]!='#') { k++; a=a+dl[dire][0]; b=b+dl[dire][1]; right(a,b,c,d); } else { dire=(dire-1+4)%4; k++; a=a+dl[dire][0]; b=b+dl[dire][1]; right(a,b,c,d); } } } return 0; } int bfs(int a,int b,int c,int d) { memset(vis,0,sizeof(vis)); vis[a][b]=1; q.push(a);q.push(b); while(!q.empty()) { int x,y,i; x=q.front();q.pop(); y=q.front();q.pop(); for(i=0;i<4;i++) { int m,n; m=x+dl[i][0]; n=y+dl[i][1]; if(m>=0&&m<h&&n>=0&&n<w&&map[m][n]!='#'&&vis[m][n]==0) { vis[m][n]=vis[x][y]+1; if(m==c&&n==d) { k=vis[m][n]; return 0; } q.push(m); q.push(n); } } } return 0; } int main() { int cas; scanf("%d",&cas); while(cas--) { scanf("%d%d",&w,&h); int i,s1,s2,e1,e2,j; for(i=0;i<h;i++) { scanf("%s",map[i]); for(j=0;j<w;j++) { if(map[i][j]=='S') { s1=i;s2=j; } if(map[i][j]=='E') { e1=i;e2=j; } } } k=1; if(s1==0) dire=3; else if(s1==h-1) dire=1; else if(s2==0) dire=2; else dire=0; j=dire; left(s1,s2,e1,e2); printf("%d ",k); dire=j;k=1; right(s1,s2,e1,e2); printf("%d ",k); bfs(s1,s2,e1,e2); printf("%d/n",k); while(!q.empty()) q.pop(); } return 0; }

http://jiyuede.blog.163.com/blog/static/33251921201022265225211/解答摘录如下:

1、至于求最短距离,毋庸置疑,肯定是bfs,这个就不多说了

2、对于向左和向右的理解上,我当初一直不明白,读了老长时间,没有看懂,到discuss里看了一个人的叙述,终于明白意思了……就是这样,一直沿着向左或向右的方向走,能走就走,不能走就回撤,所以这个dfs不能标记遍历过的点,这是很显然的。

3、dfs方向的选择,就是要保证沿着向左或者向右的方向走

#include<stdio.h> #include<queue> #include<string.h> #include<algorithm> using namespace std; struct T { int row,col; }; char chess[50][50]; int visited[50][50]; int dir[4][2]={{-1,0},{0,1},{1,0},{0,-1}}; int ldir1[4][2]={{0,-1},{-1,0},{0,1},{1,0}}; int ldir2[4][2]={{-1,0},{0,1},{1,0},{0,-1}}; int ldir3[4][2]={{0,1},{1,0},{0,-1},{-1,0}}; int ldir4[4][2]={{1,0},{0,-1},{-1,0},{0,1}}; int rdir1[4][2]={{0,1},{-1,0},{0,-1},{1,0}}; int rdir2[4][2]={{1,0},{0,1},{-1,0},{0,-1}}; int rdir3[4][2]={{0,-1},{1,0},{0,1},{-1,0}}; int rdir4[4][2]={{-1,0},{0,-1},{1,0},{0,1}}; queue<T> q; int row,col; int Min; bool flag1; bool flag2; bool flag3; int lstep; int rstep; void left(T,T); void right(T,T); void bfs(); bool check(int,int); T ori,des; int main() { int i,j,k,m,n; scanf("%d",&n); while(n--) { scanf("%d%d",&col,&row); for(i=1;i<=row;i++) { getchar(); for(j=1;j<=col;j++) { scanf("%c",&chess[i][j]); if(chess[i][j]=='S') { ori.row=i; ori.col=j; } if(chess[i][j]=='E') { des.row=i; des.col=j; } } } memset(visited,0,sizeof(visited)); while(!q.empty()) q.pop(); q.push(ori); Min=1; flag1=false; flag2=false; flag3=false; lstep=1; rstep=1; //寻找第一个可以走的点 T sec; for(i=0;i<4;i++) { if(check(dir[i][0]+ori.row,dir[i][1]+ori.col)) { sec.row=dir[i][0]+ori.row; sec.col=dir[i][1]+ori.col; break; } } left(ori,sec); right(ori,sec); printf("%d %d ",lstep,rstep); bfs(); printf("%d/n",Min); } return 0; } bool check(int x,int y) { if(x>0&&x<=row&&y>0&&y<=col) if(chess[x][y]!='#') return true; return false; } void bfs() { int i,j,k,m,n; T ch,lin; while(flag1==false) { k=q.size(); for(j=0;j<k;j++) { ch=q.front(); q.pop(); for(i=0;i<4;i++) { if(check(ch.row+dir[i][0],ch.col+dir[i][1])) { lin.row=ch.row+dir[i][0]; lin.col=ch.col+dir[i][1]; q.push(lin); if(lin.row==des.row&&lin.col==des.col) { flag1=true; break; } chess[lin.row][lin.col]='#'; } } if(flag1) break; } Min++; } } void left(T last,T cur) { int x,y; int i; T next; if(flag2) return; if(cur.row==des.row&&cur.col==des.col) { flag2=true; lstep++; return; } x=cur.row-last.row; y=cur.col-last.col; if(x==-1&&y==0) for(i=0;i<4;i++) { if(check(ldir1[i][0]+cur.row,ldir1[i][1]+cur.col)) { lstep++; next.row=ldir1[i][0]+cur.row; next.col=ldir1[i][1]+cur.col; left(cur,next); if(flag2) return; } } else if(x==0&&y==1) { for(i=0;i<4;i++) { if(check(ldir2[i][0]+cur.row,ldir2[i][1]+cur.col)) { lstep++; next.row=ldir2[i][0]+cur.row; next.col=ldir2[i][1]+cur.col; left(cur,next); if(flag2) return; } } } else if(x==1&&y==0) { for(i=0;i<4;i++) { if(check(ldir3[i][0]+cur.row,ldir3[i][1]+cur.col)) { lstep++; next.row=ldir3[i][0]+cur.row; next.col=ldir3[i][1]+cur.col; left(cur,next); if(flag2) return; } } } else { for(i=0;i<4;i++) { if(check(ldir4[i][0]+cur.row,ldir4[i][1]+cur.col)) { lstep++; next.row=ldir4[i][0]+cur.row; next.col=ldir4[i][1]+cur.col; left(cur,next); if(flag2) return; } } } } void right(T last,T cur) { int x,y,i; T next; if(flag3) return; if(cur.row==des.row&&cur.col==des.col) { flag3=true; rstep++; return; } x=cur.row-last.row; y=cur.col-last.col; if(x==-1&&y==0) for(i=0;i<4;i++) { if(check(rdir1[i][0]+cur.row,rdir1[i][1]+cur.col)) { rstep++; next.row=rdir1[i][0]+cur.row; next.col=rdir1[i][1]+cur.col; right(cur,next); if(flag3) return; } } else if(x==0&&y==1) { for(i=0;i<4;i++) { if(check(rdir2[i][0]+cur.row,rdir2[i][1]+cur.col)) { rstep++; next.row=rdir2[i][0]+cur.row; next.col=rdir2[i][1]+cur.col; right(cur,next); if(flag3) return; } } } else if(x==1&&y==0) { for(i=0;i<4;i++) { if(check(rdir3[i][0]+cur.row,rdir3[i][1]+cur.col)) { rstep++; next.row=rdir3[i][0]+cur.row; next.col=rdir3[i][1]+cur.col; right(cur,next); if(flag3) return; } } } else { for(i=0;i<4;i++) { if(check(rdir4[i][0]+cur.row,rdir4[i][1]+cur.col)) { rstep++; next.row=rdir4[i][0]+cur.row; next.col=rdir4[i][1]+cur.col; right(cur,next); if(flag3) return; } } } }

内容概要:本文介绍了一项创新性未发表的研究,即利用多元宇宙优化算法(Multiverse Optimizer, MVO)对分时电价下的需求响应与综合能源系统调度问题进行建模与求解,旨在实现能源系统的经济性、高效性与可持续性运行。该研究构建了包含多种能源设备(如光伏、风机、燃气轮机、储能系统等)及可调节负荷的综合能源系统模型,充分考虑了用户侧的需求响应行为在分时电价机制下的响应特性,通过MVO算法对系统运行成本、能源利用率、碳排放等多目标进行协同优化,实现了日前调度计划的智能决策。研究还提供了完整的MATLAB代码实现,便于研究人员复现实验、验证算法性能,并为进一步研究提供可靠的仿真基础。; 适合人群:具备一定电力系统、优化算法及MATLAB编程基础的科研人员、研究生以及从事能源互联网、综合能源系统规划与运行的技术工程师。; 使用场景及目标:① 学习并掌握多元宇宙优化算法在复杂能源系统调度中的具体应用方法;② 研究分时电价机制如何通过需求响应引导用户参与电网互动,实现削峰填谷;③ 实现综合能源系统(IES)中冷、热、电、气等多种能源的协同优化调度,以降低运行成本、提高新能源消纳能力和系统可靠性;④ 为相关领域的学术研究提供可复现的代码实例和仿真平台。; 阅读建议:此资源以MATLAB代码为核心载体,深入剖析了算法应用与系统建模的全过程。建议读者在学习时,不仅应关注代码的实现细节,更要理解其背后的数学模型、优化目标设定和约束条件的物理意义。建议结合文档中的模型描述,逐步调试代码,观察不同参数和场景下的优化结果,从而深刻掌握综合能源系统优化调度的设计思想与关键技术。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值