【BZOJ 1375】 [Baltic2002]Bicriterial routing 双调路径
来源:互联网 发布:网络爱情歌曲 编辑:程序博客网 时间:2024/04/29 10:19
1375: [Baltic2002]Bicriterial routing 双调路径
Time Limit: 5 Sec Memory Limit: 64 MBSubmit: 299 Solved: 115
[Submit][Status]
Description
来越多,因此选择最佳路径是很现实的问题。城市的道路是双向的,每条道路有固定的旅行时间以及需要支付的费用。路径由连续的道路组成。总时间是各条道路旅行时间的和,总费用是各条道路所支付费用的总和。同样的出发地和目的地,如果路径A比路径B所需时间少且费用低,那么我们说路径A比路径B好。对于某条路径,如果没有其他路径比它好,那么该路径被称为最优双调路径。这样的路径可能不止一条,或者说根本不存在。 给出城市交通网的描述信息,起始点和终点城市,求最优双条路径的条数。城市不超过100个,边数不超过300,每条边上的费用和时间都不超过100。
Input
第一行给出有多少个点,多少条边,开始点及结束点. 下面的数据用于描述这个地图
Output
有多少条最优双调路径
Sample Input
4 5 1 4
2 1 2 1
3 4 3 1
2 3 1 2
3 1 1 4
2 4 2 4
2 1 2 1
3 4 3 1
2 3 1 2
3 1 1 4
2 4 2 4
Sample Output
2
HINT
分层图上的最短路。
f[i][j]表示走到i结点,费用为j的最少时间,直接跑spfa即可。
#include <iostream>#include <algorithm>#include <cstring>#include <cstdio>#include <cstdlib>#include <queue>#define inf 0x3f3f3f3f#define maxc (n-1)*100using namespace std;struct edge{int y,ne,c,t;}e[1000];struct now{int p,c;};int tot=0,n,m;struct data{int t,f;}d[105][10005];int s,t,h[105],inq[105][10005];void Addedge(int x,int y,int co,int ti){tot++;e[tot].y=y;e[tot].ne=h[x];h[x]=tot;e[tot].c=co;e[tot].t=ti;}void spfa(){for (int i=1;i<=n;i++)for (int j=0;j<=maxc;j++)d[i][j].f=0,inq[i][j]=0,d[i][j].t=inf;queue<now> q;now x;x.p=s,x.c=0;d[s][0].f=1,d[s][0].t=0;inq[s][0]=1;q.push(x);while (!q.empty()){x=q.front();q.pop();inq[x.p][x.c]=0; for (int i=h[x.p];i;i=e[i].ne){int y=e[i].y;int co=e[i].c+x.c;if (co>maxc) continue;if (d[y][co].t>d[x.p][x.c].t+e[i].t){d[y][co].t=d[x.p][x.c].t+e[i].t;d[y][co].f=1;if (!inq[y][co]){now aa;aa.p=y,aa.c=co;q.push(aa),inq[y][co]=1;}}}}}int main(){ scanf("%d%d%d%d",&n,&m,&s,&t);for (int i=1;i<=m;i++){int x,y,ti,co;scanf("%d%d%d%d",&x,&y,&co,&ti);Addedge(x,y,co,ti);Addedge(y,x,co,ti);}spfa();int ans=0,minn=maxc+10; for (int i=0;i<=maxc;i++){if (!d[t][i].f) continue;if (d[t][i].t>=minn) continue;minn=d[t][i].t;ans++;}cout<<ans<<endl;return 0;}
wa是因为求答案时写了break,应该是continue。
其实这个题还可以进行优化:
如果存在f[i][k],满足k<j且f[i][k]<f[i][j],那么f[i][j]一定不是最优解。
因此我们可以给每一个结点建一棵线段树,维护最小值即可。
#include <iostream>#include <algorithm>#include <cstring>#include <cstdio>#include <cstdlib>#include <queue>#define inf 0x3f3f3f3f#define maxc (n-1)*100+5using namespace std;struct edge{int y,ne,c,t;}e[1000];struct now{int p,c;};int tot=0,n,m;struct data{int t,f;}d[105][10005];int s,t,h[105],inq[105][10005];struct segtree{int l,r,minn;}T[105][40005];void Addedge(int x,int y,int co,int ti){tot++;e[tot].y=y;e[tot].ne=h[x];h[x]=tot;e[tot].c=co;e[tot].t=ti;}void Build(int now,int x,int l,int r){T[now][x].l=l,T[now][x].r=r;if (l==r) {T[now][x].minn=maxc;return;}int m=(l+r)>>1;Build(now,x<<1,l,m);Build(now,(x<<1)+1,m+1,r);T[now][x].minn=maxc;}void Update(int now,int x,int p,int k){if (T[now][x].l==T[now][x].r&&T[now][x].l==p){T[now][x].minn=min(k,T[now][x].minn);return;}int m=(T[now][x].l+T[now][x].r)>>1;if (p<=m) Update(now,x<<1,p,k);else Update(now,(x<<1)+1,p,k);T[now][x].minn=min(T[now][x<<1].minn,T[now][(x<<1)+1].minn);}int Get(int now,int x,int l,int r){if (T[now][x].l>=l&&T[now][x].r<=r)return T[now][x].minn;int m=(T[now][x].l+T[now][x].r)>>1;if (r<=m) return Get(now,x<<1,l,r);if (l>m+1) return Get(now,(x<<1)+1,l,r);return min(Get(now,x<<1,l,r),Get(now,(x<<1)+1,l,r));}void spfa(){for (int i=1;i<=n;i++)for (int j=0;j<=maxc;j++)d[i][j].f=0,inq[i][j]=0,d[i][j].t=inf;queue<now> q;now x;x.p=s,x.c=0;d[s][0].f=1,d[s][0].t=0;inq[s][0]=1;Update(s,1,0,0);q.push(x);while (!q.empty()){x=q.front();q.pop();inq[x.p][x.c]=0; for (int i=h[x.p];i;i=e[i].ne){int y=e[i].y;int co=e[i].c+x.c;if (co>maxc) continue;if (d[y][co].t>d[x.p][x.c].t+e[i].t&&Get(y,1,0,co)>d[x.p][x.c].t+e[i].t){d[y][co].t=d[x.p][x.c].t+e[i].t;d[y][co].f=1;Update(y,1,co,d[y][co].t);if (!inq[y][co]){now aa;aa.p=y,aa.c=co;q.push(aa),inq[y][co]=1;}}}}}int main(){ scanf("%d%d%d%d",&n,&m,&s,&t);for (int i=1;i<=m;i++){int x,y,ti,co;scanf("%d%d%d%d",&x,&y,&co,&ti);Addedge(x,y,co,ti);Addedge(y,x,co,ti);}for (int i=1;i<=n;i++)Build(i,1,0,maxc);spfa();int ans=0,minn=maxc+10; for (int i=0;i<=maxc;i++){if (!d[t][i].f) continue;if (d[t][i].t>=minn) continue;minn=d[t][i].t;ans++;}cout<<ans<<endl;return 0;}
进入第一版~
其实没必要用线段树,因为是求前缀的最小值,直接树状数组就可以了。。
1 0
- 【BZOJ 1375】 [Baltic2002]Bicriterial routing 双调路径
- BZOJ 1375 [Baltic2002]Bicriterial routing 双调路径 SPFA
- bzoj1375[Baltic2002]Bicriterial routing 双调路径
- BZOJ 1375: [Baltic2002]Bicriterial routing 双调路径 SPFA+DP思想
- bzoj1375 [Baltic2002]Bicriterial routing 双调路径 (两个值的最短路)
- BZOJ 1375 Bicriterial routing 双调路径 (二维最短路)
- bzoj 3889: [Usaco2015 Jan]Cow Routing SPFA
- URAL 1072 Routing [最短路径]
- Routing
- Routing
- Routing
- bzoj1378: [Baltic2002]Tri
- BZOJ 3889: [Usaco2015 Jan]Cow Routing 双键值最短路
- ASP.NET MVC Framework体验:路径选择(URL Routing)
- 导航地图中Routing路径规划模块相关概念
- BZOJ-2337-XOR和路径
- bzoj 3784: 树上的路径
- BZOJ 2306: [Ctsc2011]幸福路径
- 计算机经典书籍
- iptables基础及samba配置举例
- 【重构】数据库设计
- 注册自己的log函数,拦截出错时候的错误信息
- InfoPath与SharePoint之(四)发布Form 到Form Library
- 【BZOJ 1375】 [Baltic2002]Bicriterial routing 双调路径
- C++ STL 算法:元素计数
- powerdesigner的使用教程(二)-脚本导入导出
- Scanner对象的方法总结
- CC4.5 检测二叉查找树
- (五十四)涂鸦的实现和截图的保存
- SQL语句查询出数据库中所有表的结构
- 原型模式——浅复制和深复制
- 走遍美国