zoukankan      html  css  js  c++  java
  • poj 2749 Building roads 夜

    http://poj.org/problem?id=2749

    2-sat + 二分  

    在二分里面根据情况 有时候是求大的 有时候是求小的

    这个二分里面 我分的时候

    while(l<r)

    l=mid+1;

    r=mid;

    因为 mid可能就是答案 还有就是如果最后停在 r为有边界时  r可能不是答案需要特判 一下

    代码:

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<string>
    #include<vector>
    #include<set>
    #include<queue>
    #include<stack>
    #include<cmath>
    #define LL long long
    
    using namespace std;
    
    const int N=1005;
    int head[N],I;
    struct ss
    {
        int j,next;
    }side[N*N];
    struct key
    {
        int i,j;
    }hate[N],fri[N];
    int Adist[N],Bdist[N];
    int low[N],dfn[N],f[N],deep;
    bool in[N],visited[N];
    stack<int>st;
    int ans[N*N];
    int n,m1,m2;
    void build(int x,int y)
    {
        side[I].j=y;
        side[I].next=head[x];
        head[x]=I++;
    }
    void Tarjan(int x)
    {
        visited[x]=true;
        in[x]=true;
        st.push(x);
        low[x]=dfn[x]=deep++;
        for(int t=head[x];t!=-1;t=side[t].next)
        {
            int k=side[t].j;
            if(visited[k]==false)
            {
                Tarjan(k);
                low[x]=min(low[x],low[k]);
            }else if(in[k]==true)
            {
                low[x]=min(low[x],dfn[k]);
            }
        }
        if(low[x]==dfn[x])
        {
            int k;
            do
            {
                k=st.top();
                st.pop();
                in[k]=false;
                f[k]=x;
            }while(k!=x);
        }
    }
    bool solve(int d,int s)
    {
        memset(head,-1,sizeof(head));
        I=0;
        for(int i=1;i<=n;++i)
        {
            for(int j=1;j<i;++j)
            {
                int w=0;
                if(Adist[i]+Adist[j]>d)
                {build(i,j+n);build(j,i+n);++w;}
                if(Bdist[i]+Bdist[j]>d)
                {build(i+n,j);build(j+n,i);++w;}
                if(Adist[i]+Bdist[j]+s>d)
                {build(i,j);build(j+n,i+n);++w;}
                if(Bdist[i]+Adist[j]+s>d)
                {build(i+n,j+n);build(j,i);++w;}
                if(w==4)
                return false;
            }
        }
        for(int l=1;l<=m1;++l)
        {
            build(hate[l].i,hate[l].j+n);build(hate[l].j,hate[l].i+n);
            build(hate[l].i+n,hate[l].j);build(hate[l].j+n,hate[l].i);
        }
        for(int l=1;l<=m2;++l)
        {
            build(fri[l].i,fri[l].j);build(fri[l].j,fri[l].i);
            build(fri[l].i+n,fri[l].j+n);build(fri[l].j+n,fri[l].i+n);
        }
        memset(visited,false,sizeof(visited));
        memset(in,false,sizeof(in));
        memset(f,-1,sizeof(f));
        while(!st.empty())
        st.pop();
        deep=0;
        int l;
        for(l=1;l<n;++l)
        {
            if(!visited[l])
            Tarjan(l);
            if(f[l]!=-1&&f[l]==f[l+n])
            break;
        }
        if(l<n)
        return false;
        else
        return true;
    
    }
    int main()
    {
        //freopen("data.txt","r",stdin);
        while(scanf("%d %d %d",&n,&m1,&m2)!=EOF)
        {
           int sx1,sy1,sx2,sy2;
           scanf("%d %d %d %d",&sx1,&sy1,&sx2,&sy2);
           int s=abs(sx1-sx2)+abs(sy1-sy2);
           for(int i=1;i<=n;++i)
           {
               int x,y;
               scanf("%d %d",&x,&y);
               Adist[i]=abs(x-sx1)+abs(y-sy1);
               Bdist[i]=abs(x-sx2)+abs(y-sy2);
           }
           int L=0;
           for(int i=1;i<=n;++i)
           {
               for(int j=1;j<i;++j)
               {
                   ans[++L]=Adist[i]+Adist[j];
                   ans[++L]=Bdist[i]+Bdist[j];
                   ans[++L]=Adist[i]+Bdist[j]+s;
                   ans[++L]=Bdist[i]+Adist[j]+s;
               }
           }
           for(int i=1;i<=m1;++i)
           scanf("%d %d",&hate[i].i,&hate[i].j);
           for(int i=1;i<=m2;++i)
           scanf("%d %d",&fri[i].i,&fri[i].j);
           sort(ans+1,ans+L+1);
           int l=1,r=L;
           while(l<r)
           {//cout<<l<<" "<<r<<endl;
               int mid=(l+r)/2;
               if(solve(ans[mid],s))
               r=mid;
               else
               l=mid+1;
           }
           if(!solve(ans[r],s))
           printf("-1\n");
           else
           printf("%d\n",ans[r]);
        }
        return 0;
    }
    

      

  • 相关阅读:
    优雅的使用Python之软件管理
    优雅的使用python之环境管理
    SpriteSheet精灵动画引擎
    【译】AS3利用CPU缓存
    走在网页游戏开发的路上(十一)
    自定义路径创建Cocos2d-x项目
    C++静态库与动态库
    C++对象模型
    超时空英雄传说2复仇魔神完全攻略&秘技
    从头写个http client(java)
  • 原文地址:https://www.cnblogs.com/liulangye/p/2645621.html
Copyright © 2011-2022 走看看