poj2331 Water pipe IDA*
来源:互联网 发布:兰博德网络加速下载 编辑:程序博客网 时间:2024/06/08 04:36
Description
The Eastowner city is perpetually haunted with water supply shortages, so in order to remedy this problem a new water-pipe has been built. Builders started the pipe from both ends simultaneously, and after some hard work both halves were connected. Well, almost. First half of pipe ended at a point (x1, y1), and the second half – at (x2, y2). Unfortunately only few pipe segments of different length were left. Moreover, due to the peculiarities of local technology the pipes can only be put in either north-south or east-west direction, and be connected to form a straight line or 90 degree turn. You program must, given L1, L2, … Lk – lengths of pipe segments available and C1, C2, … Ck – number of segments of each length, construct a water pipe connecting given points, or declare that it is impossible. Program must output the minimum required number of segments.
Constraints
1 <= k <= 4, 1 <= xi, yi, Li <= 1000, 1 <= Ci <= 10
Input
Input contains integers x1 y1 x2 y2 k followed by 2k integers L1 L2 … Lk C1 C2 … Ck
Output
Output must contain a single integer – the number of required segments, or −1 if the connection is impossible.
Sample Input
20 10 60 50 2 70 30 2 2
Sample Output
4
题目大意
在平面上有一个起点和一个终点,你需要用一些给定的管子将这两个点连起来,求最少需要多少管子。
输入
首先5个整数sx,sy,tx,ty,n。sx,sy代表起点坐标;tx,ty代表终点坐标;
n代表管子数量。接下来n个整数分别代表每个管子的长度,在接着n个整数分别代表每个管子的数量。
输出
一个整数代表最少的管子数。
总结
昨天学了A*和IDA*启发式搜索,一直在改这道题,后来发现就是dfs没有回溯,弄了我将近两个小时。我觉得有些无语。
先简要谈一下对A*以及IDA*的看法。
A*以及IDA*都是启发式搜索,他们都是在一般搜索的基础上增加了启发式函数(估价函数),对于一个启发式搜索,估价函数是非常重要的,估价函数通俗来讲就是一个估算到目的地要花费多少,有了一个好的估价函数,就少了很多不必要的搜索。相反,一个错误估价函数,会将你的搜索引入歧途。既然估价函数对我们这么重要,那我们应该怎么求呢?其实在不同的题目之中有不同的估价函数,比较常见的就是曼哈顿函数,通过计算两点之间绝对值之差来算。
那我们又要问A*与IDA*之间有什么区别呢?
其实很简单。A*是由bfs加估价函数构成的,而IDA*是由dfs加估价函数构成的,由于dfs不能控制深度,我们需要通过枚举深度来算,一旦出现解,必定是最优解。
回到这一道题,这一道题我们的估价函数是通过bfs不计线段数量算出来的,而实际情况是大于等于这种情况的。
WA的原因
一直b[i].num–之后忘记++了——
#include<cstdio>#include<cstdlib>#include<cstring>#include<cmath>#include<string>#include<vector>#include<stack>#include<set>#include<queue>using namespace std;const int maxn=1001,inf=1e9;int sx,sy,tx,ty,sum,ans,h1[maxn],h2[maxn],n;struct node{ int len,num;};bool dfs1(node *a,int x,int z){ int i,j; if(h2[x]==-1 || h2[x]+z>ans) return false; if(h2[x]==0){ //printf("->h2--%d___%d\n",x,z); return true; } node b[11]; for(i=1;i<=n;i++) b[i]=a[i]; for(i=1;i<=n;i++) if(b[i].num>0){ b[i].num--; if(x-b[i].len>=1) if(dfs1(b,x-b[i].len,z+1)){ //printf("->h2--%d\n",x); return true; } if(x+b[i].len<=1000) if(dfs1(b,x+b[i].len,z+1)){ //printf("->h2--%d\n",x); return true; } b[i].num++; } return false;}bool dfs(node *a,int x,int z){ int i,j; if(h1[x]==-1 || h1[x]+z>ans) return false; if(h1[x]==0){ //printf("%d__%d\n",x,z); //for(i=1;i<=n;i++) printf("%d-----",a[i].num); return dfs1(a,sy,z); } node b[11]; for(i=1;i<=n;i++) b[i]=a[i]; for(i=1;i<=n;i++) if(b[i].num>0){ b[i].num--; if(x-b[i].len>=1) if(dfs(b,x-b[i].len,z+1)){ //printf("->h1--%d----id:%d\n",x,i); return true; } if(x+b[i].len<=1000) if(dfs(b,x+b[i].len,z+1)){ //printf("->h1--%d----id:%d=====x+b[i]=%d\n",x,i,x+b[i].len); return true; } b[i].num++; } return false;}node a[11];void bfs(int *h,int st){ int i,j; queue <int> q; h[st]=0; q.push(st); while(!q.empty()){ int x; x=q.front(); q.pop(); for(i=1;i<=n;i++){ if(x-a[i].len>=1) if(h[x-a[i].len]==-1){ h[x-a[i].len]=h[x]+1; q.push(x-a[i].len); } if(x+a[i].len<=1000) if(h[x+a[i].len]==-1){ h[x+a[i].len]=h[x]+1; q.push(x+a[i].len); } } }}void id_astar(){ int i; if(sx==tx && sy==ty){ puts("0"); return; } memset(h1,-1,sizeof(h1)); memset(h2,-1,sizeof(h2)); bfs(h1,tx); bfs(h2,ty); /*for(i=1;i<=1000;i++) if(h1[i]!=-1 || h2[i]!=-1) printf("h1[%d]=%d h2[%d]=%d\n",i,h1[i],i,h2[i]);*/ for(ans=1;ans<=sum;ans++){ //if(ans==4) //system("pause"); if(dfs(a,sx,0)) break; } if(ans<=sum) printf("%d\n",ans); else puts("-1"); return;} int main(){ int i,j,k; int x1,y1,x2,y2; //freopen("test.in","r",stdin); //freopen("test.out","w",stdout); scanf("%d%d%d%d%d",&sx,&sy,&tx,&ty,&n); for(i=1;i<=n;i++) scanf("%d",&a[i].len); for(i=1;i<=n;i++){ scanf("%d",&a[i].num); sum+=a[i].num; } id_astar(); return 0;}
- POJ2331:Water pipe(IDA*)
- poj2331 Water pipe IDA*
- IDA* POJ2331 Water pipe
- #POJ2331#Water pipe(IDA*_搜索)
- POJ2331 Water pipe
- POJ2331 Water Pipe 解题报告
- poj2331 ida*
- POJ 2331 Water pipe IDA*
- poj2331 (IDA*)
- POJ2331Water pipe(IDA*)
- pku 2331 Water pipe
- POJ 2331 Water pipe 笔记
- ZOJ 2655 Water Pipe bfs 带方向状态
- IDA
- ida
- IDA*
- IDA*
- IDA*
- 机器学习实战——ch8.2 回归之预测乐高玩具价格
- Schema和xml名称空间理解笔记
- 查看数据库大小
- Java 初学者问题收集
- LightOJ 1282 (快速幂+截取前n位输出)
- poj2331 Water pipe IDA*
- vim匹配空行并删除
- 常见例题:用foreach遍历数组
- 怎么给word章节自动编号?(推荐方法二)
- The specified child already has a parent. You must call removeView() on the child's parent first
- ViewPager中动态删除Fragment的方法
- post乱码
- LightOJ 1294
- 区间DP:POJ 2955括号匹配 + NYOJ 737 石子归并(一) + No.312 Burst Balloons