【BZOJ4260】REBXOR

鏈接

BZOJ4260

解法:字典樹

處理前綴異或和和後綴異或和,然後枚舉分離位置ii,分別查詢前綴異或最大和後綴異或最大,相加即可。(注意預處理)

代碼

#include<iostream>
#include<cstdio>
#include<cstring>

using namespace std;

struct Trie{
	int root,tot,son[12800001][2];
	Trie():root(1),tot(1){memset(son,0,sizeof(son));}
	void insert(int x){
		int u=root,b[31];for(int i=0;i<31;++i)b[i]=(x&(1<<i))>>i;
		for(int i=30;~i;--i){int &v=son[u][b[i]];if(!v)v=++tot;u=v;}
	}
	int query(int u,int x,int p){
		if(p==-1)return x;
		if(son[u][1]&&(x^(1<<p))>x)return query(son[u][1],x^(1<<p),p-1);
		else if(son[u][0])return query(son[u][0],x,p-1);else return query(son[u][1],x^(1<<p),p-1);
	}
};

Trie t1,t2;
int max1[400001],max2[400002],n,a[400001],ans;

int main(){
	scanf("%d",&n);t1.insert(0),t2.insert(0);
	for(int i=1;i<=n;++i)scanf("%d",a+i);
	for(int i=1,sum=0;i<=n;++i)sum^=a[i],t1.insert(sum),max1[i]=max(max1[i-1],t1.query(t1.root,sum,30));
	for(int i=n,sum=0;i;--i)sum^=a[i],t2.insert(sum),max2[i]=max(max2[i+1],t2.query(t2.root,sum,30));
	for(int i=0;i<=n;++i)ans=max(ans,max1[i]+max2[i+1]);
	printf("%d",ans);
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章