bzoj 2834: 回家的路
题目
F.A.Qs | Home | Discuss | ProblemSet | Status | Ranklist | Contest | 入门OJ | ModifyUser DCOI | Logout | 捐赠本站 |
---|
Notice:1:注册本OJ方式请见https://www.lydsy.com/JudgeOnline/wttl/thread.php?tid=5671 2:替用户ir1d发布如下信息,希望大家能够积极支持。 OI Wiki 致力于成为一个开放自由的 OI 知识整合站点,欢迎感兴趣的同学参与贡献 https://oi-wiki.org
2834: 回家的路
Time Limit: 10 Sec Memory Limit: 128 MBSubmit: 183 Solved: 98
[Submit][Status][Discuss]
Description
Input
Output
Sample Input
2 1
1 2
1 1 2 2
1 2
1 1 2 2
Sample Output
5
HINT
N<=20000,M<=100000
Source
解法
分层图最短路,将横向与纵向分开即可。
但是只能存下可转移的点与起点和终点。
数据好像有点水,起点和终点好像一定可以换乘
代码
#include <iostream> #include <cstdio> #include <cstdlib> #include <cstring> #include <cmath> #include <algorithm> #include <cctype> #include <vector> #include <queue> #define INF 2139062143 #define MAX 0x7ffffffffffffff #define del(a,b) memset(a,b,sizeof(a)) using namespace std; typedef long long ll; template<typename T> inline void read(T&x) { x=0;T k=1;char c=getchar(); while(!isdigit(c)){if(c=='-')k=-1;c=getchar();} while(isdigit(c)){x=x*10+c-'0';c=getchar();}x*=k; } const int maxn=100000+15; int n,m,s,t,ecnt[2]; struct Q{ int x,y,id; }a[maxn]; struct Edge { int u,v,w; Edge(int u=0,int v=0,int w=0):u(u),v(v),w(w) {} }; vector<Edge> edge[2]; vector<int> G[maxn][2]; inline void add_edge(int u,int v,int w,int id) { edge[id].push_back(Edge(u,v,w)); edge[id].push_back(Edge(v,u,w)); ecnt[id]+=2; G[u][id].push_back(ecnt[id]-2); G[v][id].push_back(ecnt[id]-1); } priority_queue< pair<pair<int,int>,int> > q; int dis[maxn][2]; bool vis[maxn][2]; inline void dij() { del(dis,127);dis[s][0]=dis[s][1]=0; q.push(make_pair(make_pair(0,s),0)); q.push(make_pair(make_pair(0,s),1)); while(!q.empty()) { pair<pair<int,int>,int> Node=q.top();q.pop(); pair<int,int> node=Node.first; int id=Node.second,u=node.second,d=-node.first; if(vis[u][id]) continue; vis[u][id]=1; for(int i=0;i<G[u][id].size();i++) { Edge& e=edge[id][G[u][id][i]]; int v=e.v; if(dis[v][id]>d+e.w) { dis[v][id]=d+e.w; q.push(make_pair(make_pair(-dis[v][id],v),id)); } if(dis[v][id^1]>d+e.w+1) { dis[v][id^1]=d+e.w+1; q.push(make_pair(make_pair(-dis[v][id^1],v),id^1)); } } } printf("%d\n",(min(dis[m+2][0],dis[m+2][1])==INF)?-1:min(dis[m+2][0],dis[m+2][1])); } bool cmp1(Q a,Q b) { return (a.x^b.x)?a.x<b.x:a.y<b.y; } bool cmp2(Q a,Q b) { return (a.y^b.y)?a.y<b.y:a.x<b.x; } bool cmp3(Q a,Q b) { return a.id<b.id; } int main() { read(n),read(m); for(int i=1;i<=m;i++) {read(a[i].x),read(a[i].y);a[i].id=i;} read(a[m+1].x),read(a[m+1].y);read(a[m+2].x),read(a[m+2].y);a[m+1].id=m+1;a[m+2].id=m+2; sort(a+1,a+1+m+2,cmp1); for(int i=1;i<m+2;i++) if(a[i].x==a[i+1].x) add_edge(a[i].id,a[i+1].id,2*(a[i+1].y-a[i].y),1); sort(a+1,a+1+m+2,cmp2); for(int i=1;i<m+2;i++) if(a[i].y==a[i+1].y) add_edge(a[i].id,a[i+1].id,2*(a[i+1].x-a[i].x),0); s=m+1; dij(); return 0; }