poj 2749 Building roads
来源:互联网 发布:500个节点复杂网络仿真 编辑:程序博客网 时间:2024/05/17 06:51
把每个牧场分别和两个中转站其中一个连接。使曼哈顿距离最大值最小。
要把每个牧场拆成两个点,一个表示连到第一中转站,一个表示连到第二个中转站。
记录牧场之间的曼哈顿距离,然后二分,对于当前距离,如果满足连一条边,如果两个牧场不友好,他们不相同牧场连一条边,如果两个牧场友好,则把连到同一个牧场的点连一条边。
#include <iostream>#include <cstdio>#include <cstring>#include <algorithm>#include <cmath>using namespace std;const int maxn=1004005;const int maxm=2005;int dis[maxm],gra[maxm][maxm];int hate[maxm],frid[maxm];int hax[maxm],hay[maxm],frx[maxm],fry[maxm];int head[maxm],next[maxn],to[maxn];int dfn[maxm],low[maxm],vis[maxm],stk[maxm],scc[maxm];int tot,top,cnt,id,s1s2,fr,ht;void addEdage(int u,int v){ next[tot]=head[u],to[tot]=v,head[u]=tot++;}void init(){ memset(head,-1,sizeof(head)); memset(dfn,0,sizeof(dfn)); memset(vis,0,sizeof(vis)); tot=top=cnt=id=0;}void tarjan(int v){ dfn[v]=low[v]=++cnt; vis[v]=1; stk[++top]=v; for(int i=head[v];i!=-1;i=next[i]) { int u=to[i]; if(!dfn[u]) { tarjan(u); low[v]=min(low[v],low[u]); } else if(vis[u]) { low[v]=min(low[v],dfn[u]); } } if(low[v]==dfn[v]) { id++; while(true) { int u(stk[top--]); vis[u]=0; scc[u]=id; if(u==v) break; } }}bool judge(int mid,int n){ init(); for(int i=0;i<fr;i++) { addEdage(2*(frx[i]-1)+1,2*(fry[i]-1)+1); addEdage(2*(frx[i]-1),2*(fry[i]-1)); addEdage(2*(fry[i]-1)+1,2*(frx[i]-1)+1); addEdage(2*(fry[i]-1),2*(frx[i]-1)); } for(int i=0;i<ht;i++) { addEdage(2*(hax[i]-1)+1,2*(hay[i]-1)); addEdage(2*(hax[i]-1),2*(hay[i]-1)+1); addEdage(2*(hay[i]-1)+1,2*(hax[i]-1)); addEdage(2*(hay[i]-1),2*(hax[i]-1)+1); } for(int i=0;i<2*n;i++) { for(int j=0;j<2*n;j++) { if(gra[i][j]>mid) addEdage(i,j^1); } } for(int i=0;i<2*n;i++) if(!dfn[i])tarjan(i); for(int i=0;i<2*n;i+=2) if(scc[i]==scc[i+1]) return 0; return 1;}void solve(int n,int l,int r){ r++; int mid,tmp=r; while(l<r) { mid=(l+r)>>1; if(judge(mid,n)) r=mid; else l=mid+1; } if(r!=tmp) printf("%d\n",r); else printf("-1\n");}int main(){ //freopen("in.txt","r",stdin); int n,sx1,sy1,sx2,sy2; int l=1<<30,r=0; scanf("%d%d%d",&n,&ht,&fr); scanf("%d%d%d%d",&sx1,&sy1,&sx2,&sy2); s1s2=abs(sx1-sx2)+abs(sy1-sy2); for(int i=0,x,y;i<n;i++) { scanf("%d%d",&x,&y); dis[i*2]=abs(x-sx1)+abs(y-sy1); dis[2*i+1]=abs(x-sx2)+abs(y-sy2); } memset(gra,0,sizeof(gra)); for(int i=0;i<2*n;i++) { for(int j=i+1;j<2*n;j++) { if(i/2!=j/2) { if(i%2!=j%2) gra[i][j]=gra[j][i]=dis[i]+dis[j]+s1s2; else gra[i][j]=gra[j][i]=dis[i]+dis[j]; l=min(l,gra[i][j]); r=max(r,gra[i][j]); } } } for(int i=0;i<ht;i++) scanf("%d%d",&hax[i],&hay[i]); for(int i=0;i<fr;i++) scanf("%d%d",&frx[i],&fry[i]); solve(n,l,r); return 0;}
- POJ 2749 Building Roads
- poj 2749 Building roads
- poj 2749 building roads
- poj 2749 Building roads
- poj 2749 Building roads
- POJ-2749-Building roads
- poj-2749 Building roads
- poj 2749 Building roads #二分+2-sat
- POJ 2749 Building roads (2-sat)
- POJ 2749 Building roads(2-SAT)
- poj 2749 Building roads 2-sat
- POJ 2749 - Building roads(2-SAT+二分)
- poj 2749 Building roads 2-SAT
- POJ 2749 Building roads 已翻译
- |poj 2749|2-SAT|二分|Building roads
- POJ 2749 Building roads (2-SAT)
- POJ 3625 Building Roads
- poj 3625 Building Roads
- 一些必不可少的Sublime Text 2插件
- Android上使用sqlite,提示sqlite: not found
- 《windows核心编程系列》七谈谈用户模式下的线程同步
- C++多态的实现原理
- 不会说谎的序列
- poj 2749 Building roads
- QT中速度仪表盘控件QMeter的安装方法
- OpenGL学习笔记()多边形绘制-cullface
- 关系模式,函数依赖,范式
- TCP与UDP区别
- JAVA笔试题集合
- hdu 1108 最小公倍数
- Opencv LK光流
- Java绘图 - 如何正确绘图和出现滚动条