• 线段树逆序对(偏序)——cf1187D好题!


    /*
    排除掉所有不可能的情况,剩下的就是可行的
    1.数的数量不相同
    2.对任意一个区间进行排序,等价于可以交换任意逆序对,
        那么从1到n扫描b数组,判断是否可以将a数组中等于b[i]的值所在的位置j交换到位置i,等价于判断区间a[i,j]是否存在<b[i]的数,判完后这个数不会再用到,所以改成无穷大 
        类似于一类偏序问题,可以建立线段树为维护动态区间最小值 
    */
    #include<bits/stdc++.h>
    #include<queue>
    using namespace std;
    #define maxn 300005
    #define inf 0x3f3f3f3f
     
    int a[maxn],b[maxn],ta[maxn],tb[maxn],n;
    
    #define lson l,m,rt<<1
    #define rson m+1,r,rt<<1|1
    int Min[maxn<<2];
    void pushup(int rt){
        Min[rt]=min(Min[rt<<1],Min[rt<<1|1]);
    }
    void build(int l,int r,int rt){
        if(l==r){
            Min[rt]=a[l];
            return;
        }
        int m=l+r>>1;
        build(lson);
        build(rson);
        pushup(rt);
    }
    void update(int pos,int val,int l,int r,int rt){
        if(l==r){
            Min[rt]=val;
            return;
        }
        int m=l+r>>1;
        if(pos<=m)update(pos,val,lson);
        else update(pos,val,rson);
        pushup(rt);
    }
    int query(int L,int R,int l,int r,int rt){
        if(L<=l && R>=r)return Min[rt];
        int m=l+r>>1,res=0x3f3f3f3f;
        if(L<=m)res=min(res,query(L,R,lson));
        if(R>m)res=min(res,query(L,R,rson));
        return res;
    }
    
    queue<int>q[maxn];
    
    int main(){
        int t;
        cin>>t;
        while(t--){
            cin>>n;
            for(int i=1;i<=n;i++){
                cin>>a[i],ta[i]=a[i];
                while(q[a[i]].size())q[a[i]].pop();
            }
            for(int i=1;i<=n;i++)cin>>b[i],tb[i]=b[i];
            sort(ta+1,ta+1+n);sort(tb,tb+1+n);
            int flag=0;
            for(int i=1;i<=n;i++)
                if(ta[i]!=tb[i])flag=1;
            if(!flag){
                build(1,n,1);
                for(int i=1;i<=n;i++)
                    q[a[i]].push(i);
                for(int i=1;i<=n;i++){
                    int pos=q[b[i]].front();
                    q[b[i]].pop();
                    int tmp=query(1,pos,1,n,1);
                    update(pos,inf,1,n,1);
                    if(tmp<b[i])flag=1; 
                }
            }
            if(flag)puts("NO");
            else puts("YES");
        }
    } 
  • 相关阅读:
    editplus 快捷键
    python 堆栈
    python 矩阵转置
    python 单向链表
    python 读空的json文件
    c++ 结构体
    手把手教你如何利用Meterpreter渗透Windows系统
    vuejs npm chromedriver 报错
    强大的开源网络侦查工具:IVRE
    在vue 中使用Stylus
  • 原文地址:https://www.cnblogs.com/zsben991126/p/11115015.html
Copyright © 2020-2023  润新知