码迷,mamicode.com
首页 > 其他好文 > 详细

P4098 [HEOI2013]ALO

时间:2019-01-25 22:46:03      阅读:154      评论:0      收藏:0      [点我收藏+]

标签:oid   ace   code   line   root   def   std   max   str   

题目

P4098 [HEOI2013]ALO

为了个水题,调了快两个小时\(emmm\)

做法

暴力当然也能过,好像还不太好卡,数两两不同,所以两两限制通过特判的时间复杂度应该也是很优秀的,可惜\(juruo\)不会算,希望有\(dalao\)能求出大概的复杂度

操作的区间为[左边第二大+1,右边第二大-1]

本来想单调栈处理[左边第一大+1,右边第二大-1],但这样[左边第二大+1,左边第一大]这样的区间就没算

然后又想\(nL[i]=L[L[i]]+1,nR[i]=R[R[i]]-1\),又错了,这样\(\{4,5,7,1\}\)其中\(1\)的左区间会到达第一个数

正解:\(a\)从小到达排,每次把最小的数的位置在双向链表删掉,然后向左右边找当然,你也可以去肛主席树或平衡树

My complete code

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<string>
#include<iostream>
#include<stack>
using namespace std;
typedef long long LL;
const LL maxn=3000000;
inline LL Read(){
    LL 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<<3)+(x<<1)+c-'0',c=getchar();
    return x*f;
}
stack<LL>sta;
LL n,ans,M;
LL a[maxn],L[maxn],R[maxn],pre[maxn],nxt[maxn];
struct Trie{
    LL nod;
    LL len,val[maxn],son[maxn][2],d[40],root[maxn];
    inline void Build(LL &now,LL pre){
        val[now=++nod]=val[pre]+1;
        LL tmp(now);
        for(LL i=32;i>=1;--i){
            son[tmp][d[i]^1]=son[pre][d[i]^1];
            son[tmp][d[i]]=++nod;
            tmp=son[tmp][d[i]],pre=son[pre][d[i]];
            val[tmp]=val[pre]+1;
        }
    }
    inline void First(LL val){
        LL len(0);
        while(val){
            d[++len]=val&1;
            val>>=1;
        }
        for(LL i=len+1;i<=32;++i) d[i]=0;
    }
    inline void Insert(LL now,LL pre,LL val){
        First(val);
        Build(root[now],root[pre]);
    }
    inline LL Query(LL pre,LL now){
        LL ans(0);
        for(LL i=32;i>=1;--i){
            if(val[son[now][d[i]^1]]-val[son[pre][d[i]^1]]>0){
                ans|=(1<<(i-1));
                now=son[now][d[i]^1],pre=son[pre][d[i]^1];
            }else{
                now=son[now][d[i]],pre=son[pre][d[i]];
            }
        }return ans;
    }
    inline LL Solve(LL pre,LL now,LL val){
        First(val);
        return Query(root[pre-1],root[now]);
    }
}T;
struct node{
    LL val,id;
    bool operator <(const node &x)const{
        return val<x.val;
    }
}p[maxn];
int main(){
    n=Read();
    for(LL i=1;i<=n;++i){
        a[i]=Read();
        T.Insert(i,i-1,a[i]);
        p[i]=(node){a[i],i};
        pre[i]=i-1;nxt[i]=i+1;
    }
    pre[0]=1; nxt[n]=n;
    sort(p+1,p+1+n);
    for(LL i=1;i<=n;++i){
        LL now(p[i].id);
        nxt[pre[now]]=nxt[now],pre[nxt[now]]=pre[now];
        L[now]=pre[pre[now]],R[now]=nxt[nxt[now]];
    }
    for(LL i=1;i<=n;++i)
            ans=max(ans,T.Solve(L[i]+1,R[i]-1,a[i]));
    printf("%lld",ans);
    return 0;
}/*
*/

P4098 [HEOI2013]ALO

标签:oid   ace   code   line   root   def   std   max   str   

原文地址:https://www.cnblogs.com/y2823774827y/p/10321749.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!