zoukankan      html  css  js  c++  java
  • BZOJ4383 Pustynia(线段树+拓扑排序)

      线段树优化建图暴力拓扑排序即可。对于已确定的数,拓扑排序时dp,每个节点都尽量取最大值,如果仍与已确定值矛盾则无解。叶子连出的边表示大于号,其余边表示大于等于。

    #include<iostream> 
    #include<cstdio>
    #include<cmath>
    #include<cstdlib>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    #define ll long long
    #define N 100010
    #define inf 1000000000
    char getc(){char c=getchar();while ((c<'A'||c>'Z')&&(c<'a'||c>'z')&&(c<'0'||c>'9')) c=getchar();return c;}
    int gcd(int n,int m){return m==0?n:gcd(m,n%m);}
    int read()
    {
        int x=0,f=1;char c=getchar();
        while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
        while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();
        return x*f;
    }
    int n,s,m,a[N<<4],b[N],c[N],p[N<<4],id[N],pos[N<<4],degree[N<<4],q[N<<4],t,root,cnt;
    bool flag[N];
    struct data{int to,nxt;
    }edge[N<<7];
    struct data2{int l,r;
    }tree[N<<2];
    void addedge(int x,int y){t++;degree[y]++;edge[t].to=y,edge[t].nxt=p[x],p[x]=t;}
    void build(int &k,int l,int r)
    {
        k=++cnt;a[k]=inf;
        if (l==r) {id[l]=k,pos[k]=l;if (flag[l]) a[k]=c[l];return;}
        int mid=l+r>>1;
        build(tree[k].l,l,mid);
        build(tree[k].r,mid+1,r);
        addedge(k,tree[k].l),
        addedge(k,tree[k].r);
    }
    void add(int p,int k,int l,int r,int x,int y)
    {
        if (l==x&&r==y) {addedge(p,k);return;}
        int mid=l+r>>1;
        if (y<=mid) add(p,tree[k].l,l,mid,x,y);
        else if (x>mid) add(p,tree[k].r,mid+1,r,x,y);
        else add(p,tree[k].l,l,mid,x,mid),add(p,tree[k].r,mid+1,r,mid+1,y);
    }
    bool topsort()
    {
        int head=0,tail=0;for (int i=1;i<=cnt;i++) if (!degree[i]) q[++tail]=i;
        while (head<tail)
        {
            int x=q[++head],y=a[x]-(pos[x]>0);
            for (int i=p[x];i;i=edge[i].nxt)
            {
                degree[edge[i].to]--;
                if (flag[pos[edge[i].to]])
                {
                    if (a[edge[i].to]>y) return cout<<"NIE"<<endl,0;
                }
                else a[edge[i].to]=min(a[edge[i].to],y);
                if (!degree[edge[i].to]) q[++tail]=edge[i].to;
            }
        }
        if (tail<cnt) return cout<<"NIE"<<endl,0;
        else return cout<<"TAK"<<endl,1;
    }
    int main()
    {
    #ifndef ONLINE_JUDGE
        freopen("bzoj4383.in","r",stdin);
        freopen("bzoj4383.out","w",stdout);
        const char LL[]="%I64d
    ";
    #else
        const char LL[]="%lld
    ";
    #endif
        n=read(),s=read(),m=read();
        for (int i=1;i<=s;i++)
        {
            int x=read(),y=read();
            c[x]=y;flag[x]=1;
        }
        build(root,1,n);
        for (int i=1;i<=m;i++)
        {
            int l=read(),r=read(),k=read();
            for (int j=1;j<=k;j++) b[j]=read();
            b[0]=l-1,b[k+1]=r+1;
            cnt++;a[cnt]=inf;
            for (int j=1;j<=k+1;j++)
            if (b[j-1]+1<=b[j]-1) add(cnt,root,1,n,b[j-1]+1,b[j]-1);
            for (int j=1;j<=k;j++) addedge(id[b[j]],cnt);
        }
        if (topsort()) for (int i=1;i<=n;i++) printf("%d ",a[id[i]]);
        return 0;
    }
  • 相关阅读:
    C/C++&java communicate with each other 之 video file-streaming
    C/C++&java communicate with each other 之 video snapshot
    protobuf io 代码阅读
    利用逆波兰表达式,二叉树对sql语句解析
    cocos2d-x 添加sqlite3 时 报 lua_Number 错误
    error LNK2019: 无法解析的外部符号 _acosh,该符号在函数 _acoshFunc 中被引用
    visual studio 运行程序在副显示器上
    lua table 中#,getn,maxn 的区别
    'Cordova/CDVViewController.h' file not found
    [ISSUE]cannot run on the selected destination
  • 原文地址:https://www.cnblogs.com/Gloid/p/10285360.html
Copyright © 2011-2022 走看看