zoukankan      html  css  js  c++  java
  • bzoj 3261: 最大异或和 可持久化Trie

    题目大意:

    http://www.lydsy.com/JudgeOnline/problem.php?id=3261

    题解

    首先我们转化一下,设sum[x]表示1~x的异或和
    这样我们知道原来的询问转化为
    在[l-1,r-1]内选择一个值,设为y
    最大化y^sum[n]^x,其中sum[n]^x是一开始的给定值
    那么问题就转化成了在一个区间内求一个数和已知数异或最大
    所以我们直接裸上Trie树可以搞定
    但是对于这个东西是要查一个区间内的,所以我们可持久化一下就好了

    #include <queue>
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    using namespace std;
    typedef long long ll;
    inline void read(int &x){
    	x=0;char ch;bool flag = false;
    	while(ch=getchar(),ch<'!');if(ch == '-') ch=getchar(),flag = true;
    	while(x=10*x+ch-'0',ch=getchar(),ch>'!');if(flag) x=-x;
    }
    const int maxn = 600010;
    struct Node{
    	Node *ch[2];
    	int ed;
    }*null,*rt[maxn];
    Node mem[maxn*28],*it;
    inline void init(){
    	it = mem;null = it++;
    	null->ch[0] = null->ch[1] = null;
    	null->ed = 0;
    }
    Node *insert(Node *rt,int x,int d){
    	Node *p = it++;(*p = *rt);
    	p->ed++;
    	if(d == -1) return null;
    	if( ( x & (1 << (d-1) ) )) p->ch[1] = insert(p->ch[1],x,d-1);
    	else p->ch[0] = insert(p->ch[0],x,d-1);
    	return p;
    }
    int ans = 0;
    void query(Node *x,Node *y,int val,int d){
    	if(d == 0) return ;
    	int id = (val&(1 << (d-1)));
    	if(id){
    		if(y->ch[0]->ed - x->ch[0]->ed > 0){
    			ans ^= (1 << (d-1));
    			query(x->ch[0],y->ch[0],val,d-1);
    		}else query(x->ch[1],y->ch[1],val,d-1);
    	}else{
    		if(y->ch[1]->ed - x->ch[1]->ed > 0){
    			ans ^= (1 << (d-1));
    			query(x->ch[1],y->ch[1],val,d-1);
    		}else query(x->ch[0],y->ch[0],val,d-1);
    	}
    }
    int a[maxn];
    int main(){
    	init();rt[0] = null;
    	int n,m;read(n);read(m);
    	for(int i=1;i<=n;++i){
    		read(a[i]);a[i]^=a[i-1];
    		rt[i] = insert(rt[i-1],a[i],26);
    	}
    	char ch;int l,r,x;
    	while(m--){
    		while(ch=getchar(),ch<'!');
    		read(l);
    		if(ch == 'A'){
    			a[n+1] = l;a[n+1] ^= a[n];
    			rt[n+1] = insert(rt[n],a[n+1],26);
    			++n;
    		}else{
    			read(r);read(x);
    			if(l == r){
    				printf("%d
    ",a[n]^a[l-1]^x);
    				continue;
    			}
    			--l;--r;x ^= a[n];
    			ans = 0;
    			bool flag = false;
    			if(l == 0){
    				l = 1;
    				flag = true;
    			}
    			query(rt[l-1],rt[r],x,26);
    			if(flag) ans = max(ans,x);
    			printf("%d
    ",ans);
    		}
    	}
    	getchar();getchar();
    	return 0;
    }
    
  • 相关阅读:
    kafka 控制台命令
    VMware centos7 如何配置静态ip并且可上网
    kafka学习-坑篇
    IDEA中Git的更新、提交、还原方法
    深入理解Java的接口和抽象类
    java动态代理实现与原理详细分析
    注解 @EnableFeignClients 工作原理
    com.mysql.cj.jdbc.Driver 新特性jdbc.url连接供参考
    插入数据库中文乱码
    logback配置文件
  • 原文地址:https://www.cnblogs.com/Skyminer/p/6427219.html
Copyright © 2011-2022 走看看