POJ1915 双向广度优先搜索
来源:互联网 发布:软件人才缺口多少 编辑:程序博客网 时间:2024/06/08 04:26
双向广度优先搜索算法:初始状态(正向搜索)和目标状态(逆向搜索)同时向中间搜,当两个方向的搜索生成同一子状态时,搜索结束;一般用来解决最小等最优问题;
如何判断是否生成了同一子状态:(1)用标记数组,若某一状态未被遍历到,则为0,正向遍历到为1,逆向遍历到为2,当遍历到某一状态时,判断一下其对应标记数组的值;(2)本题(poj1915)代码;
#include<cstdio>#include<iostream>#include<queue>;using namespace std;#define Maxn 309struct node{ int x,y;};//坐标节点int n;//图的大小int fstep[Maxn][Maxn],bstep[Maxn][Maxn];//记录正向搜索和逆向搜索步数int dir[8][2] = {-1,-2,-2,-1,-2,1,-1,2,1,2,2,1,2,-1,1,-2};bool isok(node a){ if (a.x < 0 || a.x >= n || a.y < 0 || a.y >= n) return false; return true;}int BBFS(node a,node b){ if (a.x == b.x && a.y == b.y) { return 0; }//如果起点和终点一样,则返回0 int i,j; queue<node>q1,q2; for (i = 0; i < n; ++i) { for (j = 0; j < n; ++j) fstep[i][j] = bstep[i][j] = -1; }//步数初始化 fstep[a.x][a.y] = 0;//起点步数=0 bstep[b.x][b.y] = 0;//终点步数=0 q1.push(a); q2.push(b); while (!q1.empty() && !q2.empty()) { /*如果起点能够到达终点的话,那么两个队列是不可能为空的,如果有一个队列为空 表明某一方向的搜索已经无法再继续下去,无路可走了,换言之,也没有路可以走 到这里,说明起点与终点是不可达的,就可以结束搜索了*/ node tt,t1,t2; if (!q1.empty()) { t1 = q1.front(); q1.pop(); for (i = 0; i < 8; ++i) { tt.x = t1.x + dir[i][0]; tt.y = t1.y + dir[i][1]; if (isok(tt)) { if (fstep[tt.x][tt.y] == -1) { fstep[tt.x][tt.y] = fstep[t1.x][t1.y] + 1; q1.push(tt); } if (bstep[tt.x][tt.y] != -1)//判断是否生成了同一子状态 return fstep[tt.x][tt.y] + bstep[tt.x][tt.y]; //达到子状态的那一步上面已经走了,故返回值不需要再加一 } } } if (!q2.empty()) { t2 = q2.front(); q2.pop(); for (i = 0; i < 8; ++i) { tt.x = t2.x + dir[i][0]; tt.y = t2.y + dir[i][1]; if (isok(tt)) { if (bstep[tt.x][tt.y] == -1) { bstep[tt.x][tt.y] = bstep[t2.x][t2.y] + 1; q2.push(tt); } if (fstep[tt.x][tt.y] != -1)//判断是否生成了同一子状态 return bstep[tt.x][tt.y] + fstep[tt.x][tt.y]; //达到子状态的那一步上面已经走了,故返回值不需要再加一 } } } }}int main(){ int t,ans; struct node a,b; while (~scanf("%d",&t)) { while (t--) { scanf("%d",&n); scanf("%d%d%d%d",&a.x,&a.y,&b.x,&b.y); ans = BBFS(a,b); printf("%d\n",ans); } } return 0;}/*这题其实还可以再优化一下,就是入队列时,可以用一个标记数组判断一下该状态是否已经在队列里了只不过要用到两个标记数组分别判断,这样写的话,代码感觉有点乱,反正能过,就算了,知道就行*/
0 0
- POJ1915 双向广度优先搜索
- BFS广度优先搜索 poj1915
- poj1915 Knight Moves 双向广度搜索
- POJ1915 - Knight Moves - 广度优先搜索
- 双向广度优先搜索
- 双向广度优先搜索法。
- 双向广度优先搜索法
- 双向广度优先搜索(介绍)
- 双向广度优先搜索(介绍)
- 双向广度优先搜索算法框架
- HDU 1401 Solitaire(双向广度优先搜索)
- 学习双向广度优先搜索之前的临时感想;
- pku 1915 Knight Moves(双向广度优先搜索)
- POJ1729 Jack and Jill (双向广度优先搜索, DBFS)
- 八数码问题——双向广度优先搜索解决
- HDU 3095 Eleven puzzle(双向广度优先搜索)
- BFS广度优先搜索(12)--hdu3085(双向BFS)(进阶题)
- 广度优先搜索寻找最优路径、以及双向广度搜索算法
- 文件的下载
- 国外的php mcv框架
- hdu 3572 Task Schedule(网络流最大流)
- 线程池的原理及实现
- instanceof, isinstance,isAssignableFrom的区别
- POJ1915 双向广度优先搜索
- 改变Activity在当前任务堆栈中的顺序
- GRE写作必备句型
- HDU 2578 Dating with girls(1)
- IOS - 登录界面
- UVALive 6510 Stickers
- Python学习笔记-生成器
- JavaScript/jQuery WebIM 及时聊天通信工具 本地客户端
- PendingIntent