zoukankan      html  css  js  c++  java
  • bzoj4260 Codechef REBXOR

    Description

    Input

    输入数据的第一行包含一个整数N,表示数组中的元素个数。
    第二行包含N个整数A1,A2,…,AN。

    Output

    输出一行包含给定表达式可能的最大值。
     
    dp求出:
    对每个r1,A[l1]^A[l1+1]^...^A[r1]的最大值
    对每个l2,A[l2]^A[l2+1]^...^A[r2]的最大值
    对每个i,A[l1]^A[l1+1]^...^A[r1]的最大值lm[i] (r1≤i,1≤i≤n)
    对每个i,A[l2]^A[l2+1]^...^A[r2]的最大值rm[i] (l2≥i,1≤i≤n)
    ans=max{lm[i]+rm[i+1]} (1≤i<n)
    暴力求复杂度为O(n3),预处理异或前缀和后缀和可降至O(n2)
    再用trie优化取最大值的过程可达到O(32n)
    #include<cstdio>
    const int N=400005;
    int n,ans=0;
    int v[N];
    int ls[N],rs[N];
    int lm[N],rm[N];
    struct node{
        node*ch[2];
        node(){
            ch[0]=ch[1]=0;
        }
    };
    node ns[64*N];
    int np=0;
    inline node*new_node(){
        return ns+np++;
    }
    struct trie{
        node*rt;
        trie(){
            rt=new_node();
        }
        void insert(int x){
            node*w=rt;
            for(int i=30;i>=0;i--){
                int a=x>>i&1;
                if(w->ch[a])w=w->ch[a];
                else w=w->ch[a]=new_node();
            }
        }
        int max(int x){
            int v=0;
            node*w=rt;
            for(int i=30;i>=0;i--){
                int a=(x>>i&1)^1;
                if(w->ch[a])w=w->ch[a],v|=a<<i;
                else w=w->ch[a^1],v|=(a^1)<<i;
            }
            return v^x;
        }
    };
    trie tr;
    int main(){
        scanf("%d",&n);
        for(int i=1;i<=n;i++){
            scanf("%d",v+i);
            ls[i]=ls[i-1]^v[i];
        }
        for(int i=n;i>=1;i--)rs[i]=rs[i+1]^v[i];
        for(int i=1;i<n;i++){
            tr.insert(rs[i]);
            lm[i]=tr.max(rs[i+1]);
        }
        tr=trie();
        for(int i=n;i>1;i--){
            tr.insert(ls[i]);
            rm[i]=tr.max(ls[i-1]);
        }
        for(int i=2;i<n;i++){
            if(lm[i]<lm[i-1])lm[i]=lm[i-1];
        }
        for(int i=n-1;i>1;i--){
            if(rm[i]<rm[i+1])rm[i]=rm[i+1];
        }
        for(int i=1;i<n;i++){
            if(lm[i]+rm[i+1]>ans)ans=lm[i]+rm[i+1];
        }
        printf("%d",ans);
        return 0;
    }
     
  • 相关阅读:
    CTeX里面CTRL-Space和中文输入法的冲突问题解决
    用LaTeX画树形结构
    统计学howto
    Lights Out Game
    ubuntu下安装 Source insight
    github常用命令
    编程珠玑:第7章(初略估算)的阅读体会
    在windows上安装common lisp开发环境
    睡眠十律:程序员必看
    网络和服务器编程
  • 原文地址:https://www.cnblogs.com/ccz181078/p/5185580.html
Copyright © 2011-2022 走看看