BZOJ3387: [Usaco2004 Dec]Fence Obstacle Course栅栏行动
2016-08-22 08:30
337 查看
题目大意:给定一个初始点和n个与x轴平行的y轴坐标互不相同的栅栏,问水平距离至少移动多少能使得从该初始点回到原点且不从中间跨越任何一条栅栏
首先可以确定,最终行进的路线一定可以等价于在几个栅栏的边界和起点终点间连线产生的路径,也就是说只有栅栏的边界是有用的,所以我们可以在这些点上建边跑最短路
但是这样的话边数是N^2级别的,所以我们要优化一下建图
考虑什么样的边是有效的,对于一个栅栏端点来说,只有向上第一个拦住他的栅栏是有效的,因为其他的栅栏都可以通过垂直向上走来绕过去而这个不能
所以我们就可以只将每个点与向上第一个拦住他的栅栏的两个端点连边,这样可以将边数降成O(N)级别的了
具体实现可以用set
首先可以确定,最终行进的路线一定可以等价于在几个栅栏的边界和起点终点间连线产生的路径,也就是说只有栅栏的边界是有用的,所以我们可以在这些点上建边跑最短路
但是这样的话边数是N^2级别的,所以我们要优化一下建图
考虑什么样的边是有效的,对于一个栅栏端点来说,只有向上第一个拦住他的栅栏是有效的,因为其他的栅栏都可以通过垂直向上走来绕过去而这个不能
所以我们就可以只将每个点与向上第一个拦住他的栅栏的两个端点连边,这样可以将边数降成O(N)级别的了
具体实现可以用set
#include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #include<set> #include<map> #define N 1000010 using namespace std; set<int>S; map<int,int>P; int to ,nxt ,pre ,w ,cnt; void ae(int ff,int tt,int ww) { cnt++; to[cnt]=tt; nxt[cnt]=pre[ff]; w[cnt]=ww; pre[ff]=cnt; } int q[10*N],h,t; int d ; bool zai ; void spfa() { int i,j,x,y; memset(d,0x3f3f3f3f,sizeof(d)); d[1]=0;q[1]=1; h=t=1; while(h<=t) { x=q[h];h++;zai[x]=false; for(i=pre[x];i;i=nxt[i]) { j=to[i]; if(d[j]>d[x]+w[i]) { d[j]=d[x]+w[i]; if(!zai[j]) { t++; q[t]=j; zai[j]=true; } } } } } int main() { int k,s; scanf("%d%d",&k,&s); int i,j; int cn=1; P[0]=1;S.insert(0); int x,y; set<int>::iterator it; for(i=1;i<=k;i++) { scanf("%d%d",&x,&y); it=S.lower_bound(x); while(it!=S.end()&&(*it)<=y) { j=(*it); ae(P[j],cn+1,j-x); ae(P[j],cn+2,y-j); it++; S.erase(j); } cn++;P[x]=cn; cn++;P[y]=cn; S.insert(x);S.insert(y); } cn++; for(it=S.begin();it!=S.end();it++) ae(P[(*it)],cn,abs(s-(*it))); spfa(); printf("%d",d[cn]); }
相关文章推荐
- BZOJ3387 [Usaco2004 Dec]Fence Obstacle Course栅栏行动
- BZOJ3387 [USACO2004 Dec] Fence Obstacle Course栅栏行动
- poj 2376 && bzoj 3389: [Usaco2004 Dec]Cleaning Shifts安排值班(贪心)
- 【BZOJ3387】[Usaco2004 Dec]Fence Obstacle Course栅栏行动 线段树
- 【BZOJ】3390: [Usaco2004 Dec]Bad Cowtractors牛的报复
- BZOJ3389: [Usaco2004 Dec]Cleaning Shifts安排值班
- bzoj 3390: [Usaco2004 Dec]Bad Cowtractors牛的报复 -- 最大生成树
- BZOJ3390: [Usaco2004 Dec]Bad Cowtractors牛的报复
- 3389: [Usaco2004 Dec]Cleaning Shifts安排值班 (最短路)
- 3389: [Usaco2004 Dec]Cleaning Shifts安排值班
- bzoj 3389: [Usaco2004 Dec]Cleaning Shifts安排值班 -- 贪心
- 【bzoj3389】[Usaco2004 Dec]Cleaning Shifts安排值班
- BZOJ3391: [Usaco2004 Dec]Tree Cutting网络破坏
- 3390: [Usaco2004 Dec]Bad Cowtractors牛的报复
- bzoj3391 [Usaco2004 Dec]Tree Cutting网络破坏(dfs)
- BZOJ 3391: [Usaco2004 Dec]Tree Cutting网络破坏(搜索)
- 【BZOJ】3390: [Usaco2004 Dec]Bad Cowtractors牛的报复(kruskal)
- BZOJ 3391: [Usaco2004 Dec]Tree Cutting网络破坏( dfs )
- BZOJ 3390: [Usaco2004 Dec]Bad Cowtractors牛的报复(最大生成树)
- bzoj3389:[Usaco2004 Dec]Cleaning Shifts安排值班