zoukankan      html  css  js  c++  java
  • 【ARC069F】Flags【2-SAT】【二分】【线段树】

    题解:二分答案+线段树优化连边+2-SAT。
    二分答案mid,可以发现每个点要向连续的一段区间内的点连边,离散化后线段树优化连边即可。然后跑2-SAT判定是否有解。

    #include<cstdio>
    #include<cmath>
    #include<cstring>
    #include<algorithm>
    #include<map>
    using namespace std;
    const int N=10005,M=1000005,K=60005;
    int n,l,r,mid,ans,cnt,x[N],y[N],h[N*2],id[N*2],head[K],to[M],nxt[M];
    int idx,tot,dfn[K],low[K],scc[K],stk[K];
    map<int,int> mp;
    void adde(int u,int v){
        to[++cnt]=v;
        nxt[cnt]=head[u];
        head[u]=cnt;
    }
    namespace sgt{
        int root,tot,ch[K][2];
        void init(){
            root=tot=0;
        }
        void build(int &o,int l,int r){
            if(l==r){
                o=id[l];
                return;
            }
            o=++tot;
            int mid=(l+r)/2;
            build(ch[o][0],l,mid);
            build(ch[o][1],mid+1,r);
            adde(o,ch[o][0]);
            adde(o,ch[o][1]);
        }
        void update(int o,int l,int r,int L,int R,int x){
            if(L<=l&&R>=r){
                adde(x,o);
                return;
            }
            int mid=(l+r)/2;
            if(L<=mid){
                update(ch[o][0],l,mid,L,R,x);
            }
            if(R>mid){
                update(ch[o][1],mid+1,r,L,R,x);
            }
        }
    }
    void tarjan(int u){
        dfn[u]=low[u]=++idx;
        stk[++stk[0]]=u;
        int v;
        for(int i=head[u];i;i=nxt[i]){
            v=to[i];
            if(!dfn[v]){
                tarjan(v);
                low[u]=min(low[u],low[v]);
            }else if(!scc[v]){
                low[u]=min(low[u],dfn[v]);
            }
        }
        if(low[u]==dfn[u]){
            tot++;
            do{
                scc[stk[stk[0]]]=tot;
            }while(stk[stk[0]--]!=u);
        }
    }
    void init(){
        cnt=idx=tot=0;
        memset(head,0,sizeof(head));
        memset(dfn,0,sizeof(dfn));
        memset(low,0,sizeof(low));
        memset(scc,0,sizeof(scc));
        sgt::init();
    }
    bool check(){
        init();
        sgt::tot=2*n;
        sgt::build(sgt::root,1,h[0]);
        for(int i=1;i<=n;i++){
            int l=lower_bound(h+1,h+h[0]+1,h[x[i]]-mid+1)-h;
            int r=upper_bound(h+1,h+h[0]+1,h[x[i]]+mid-1)-h-1;
            if(l<=r){
                if(l<x[i]){
                    sgt::update(sgt::root,1,h[0],l,x[i]-1,i+n);
                }
                if(x[i]<r){
                    sgt::update(sgt::root,1,h[0],x[i]+1,r,i+n);
                }
            }
            l=lower_bound(h+1,h+h[0]+1,h[y[i]]-mid+1)-h;
            r=upper_bound(h+1,h+h[0]+1,h[y[i]]+mid-1)-h-1;
            if(l<=r){
                if(l<y[i]){
                    sgt::update(sgt::root,1,h[0],l,y[i]-1,i);
                }
                if(y[i]<r){
                    sgt::update(sgt::root,1,h[0],y[i]+1,r,i);
                }
            }
        }
        for(int i=1;i<=sgt::tot;i++){
            if(!dfn[i]){
                tarjan(i);
            }
        }
        for(int i=1;i<=n;i++){
            if(scc[i]==scc[i+n]){
                return false;
            }
        }
        return true;
    }
    int main(){
        scanf("%d",&n);
        for(int i=1;i<=n;i++){
            scanf("%d%d",&x[i],&y[i]);
            h[++h[0]]=x[i];
            h[++h[0]]=y[i];
        }
        sort(h+1,h+h[0]+1);
        for(int i=1;i<=h[0];i++){
            if(h[i]!=h[i-1]){
                mp[h[i]]=i;
            }
        }
        for(int i=1;i<=n;i++){
            int tmp=x[i];
            x[i]=mp[tmp];
            mp[tmp]++;
            tmp=y[i];
            y[i]=mp[tmp];
            mp[tmp]++;
            id[x[i]]=i;
            id[y[i]]=i+n;
        }
        l=0,r=1e9;
        while(l<=r){
            mid=(l+r)/2;
            if(check()){
                ans=mid;
                l=mid+1;
            }else{
                r=mid-1;
            }
        }
        printf("%d
    ",ans);
        return 0;
    }
  • 相关阅读:
    致21岁的自己
    nginx 入门实战
    软件测试的分类
    Springboot 使用 Jedis
    NodeJS模块、包、NPM
    NodeJS介绍
    毫秒必争,前端网页性能最佳实践--转载
    IT主要在线学习网站
    电商峰值系统架构设计--转载
    查看w3wp进程占用的内存及.NET内存泄露,死锁分析--转载
  • 原文地址:https://www.cnblogs.com/2016gdgzoi471/p/9476837.html
Copyright © 2011-2022 走看看