BZOJ3261: 最大异或和(可持续化Trie)

来源:互联网 发布:快手直播配音软件 编辑:程序博客网 时间:2024/05/29 09:51

传送门

题意:
给定一个非负整数序列 {a},初始长度为 N。
有 M个操作,有以下两种操作类型:

1 、A x:添加操作,表示在序列末尾添加一个数 x,序列的长度 N+1。
2 、Q l r x:询问操作,你需要找到一个位置 p,满足 l<=p<=r,使得:

a[p] xor a[p+1] xor … xor a[N] xor x 最大,输出最大是多少。

题解:
可持续化Trie。
其实有点像主席树。答案相当于求(a1a2...an)(a1a2...ap)x
只需要记录第二部分就好了,用类似主席树的思想持续化Trie树,贪心找即可。

#include<bits/stdc++.h>using namespace std;struct IO{    streambuf *ib,*ob;    inline void init(){        ios::sync_with_stdio(false);        cin.tie(NULL),cout.tie(NULL);        ib=cin.rdbuf();ob=cout.rdbuf();    }    inline int read(){        char ch=ib->sbumpc();int i=0,f=1;        while(!isdigit(ch)){if(ch=='-')f=-1;ch=ib->sbumpc();}        while(isdigit(ch)){i=(i<<1)+(i<<3)+ch-'0';ch=ib->sbumpc();}        return i*f;    }    inline void W(int x){        static int buf[50];        if(!x){ob->sputc('0');ob->sputc('\n');return;}        if(x<0){ob->sputc('-');x=-x;}        while(x){buf[++buf[0]]=x%10;x/=10;}        while(buf[0])        {ob->sputc(buf[buf[0]--]+'0');}        ob->sputc('\n');    }}io;const int INF=0x3f3f3f3f;const int Maxn=6e5+50;const int Maxlen=26;int n,m,nowval;struct node{    node *lc,*rc;    int sze;    inline void upt(){        sze=lc->sze+rc->sze;    }}Pool[Maxn<<6],*pool=Pool,*null=Pool,*rt[Maxn];inline node* newnode(){    ++pool;    pool->lc=pool->rc=null;    return pool;}inline void insert(node* x,node*& y,int nowdep,int val){    y=newnode();y->lc=x->lc;y->rc=x->rc;y->sze=x->sze;y->sze++;    if(!nowdep)return;    if(val&(1<<(nowdep-1)))insert(x->rc,y->rc,nowdep-1,val);    else insert(x->lc,y->lc,nowdep-1,val);}inline int query(node *x,node *y,int nowdep,int v,int ans){    if(!nowdep)return ans;    int t=v&(1<<(nowdep-1));    if(t){        if(y->lc->sze-x->lc->sze)return query(x->lc,y->lc,nowdep-1,v,ans|(1<<(nowdep-1)));        else return query(x->rc,y->rc,nowdep-1,v,ans);    }    else{        if(y->rc->sze-x->rc->sze)return query(x->rc,y->rc,nowdep-1,v,ans|(1<<(nowdep-1)));        else return query(x->lc,y->lc,nowdep-1,v,ans);    }}inline void decode(int x){    static int buf[50];    if(!x){io.ob->sputc('0');return;}    while(x){buf[++buf[0]]=x%2;x>>=1;}    while(buf[0])io.ob->sputc(buf[buf[0]--]+'0');}int main(){    io.init();n=io.read(),m=io.read();null->lc=null->rc=null;    for(int i=0;i<=n+m+1;i++)rt[i]=null;    nowval=0;insert(rt[0],rt[1],Maxlen,0);    for(int i=1;i<=n;i++){        nowval^=io.read();        insert(rt[i],rt[i+1],Maxlen,nowval);    }    for(int i=1;i<=m;i++){        static char ch[2];        cin>>(ch+1);        if(ch[1]=='A'){            nowval^=io.read();n++;            insert(rt[n],rt[n+1],Maxlen,nowval);        }        else {            int l=io.read(),r=io.read(),x=io.read();            io.W(query(rt[l-1],rt[r],Maxlen,x^nowval,0));        }    }}
原创粉丝点击