HDU 5536 Chip Factory 字典树+贪心

给你n个数,a1....an,求(ai+aj)^ak最大的值,i不等于j不等于k

思路:先建字典树,暴力i,j每次删除他们,然后贪心找k,再恢复i,j,每次和答案取较大的,就是答案,有关异或的貌似很多都用字典树,也是醉了

/*Problem : 5536 ( Chip Factory )     Judge Status : Accepted
RunId : 15506230    Language : G++    Author : qianbi08*/

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cmath>
#include <algorithm>
#include<cstring>
using namespace std;
const int maxn=300005;
int node[maxn][2],cnt,re[maxn];
int a[1005];
int newnode()
{
    ++cnt;
    node[cnt][0]=node[cnt][1]=-1;
    re[cnt]=0;
    return cnt;
}
void update(int v,int d)
{
    int u=0;
    for(int i=30; i>=0; --i)
    {
        int c=(v>>i)&1;
        if(node[u][c]==-1)
            node[u][c]=newnode();
        u=node[u][c];
        re[u]+=d;
    }
}
int getans(int v)
{
    int u=0,ans=0;
    for(int i=30; i>=0; --i)
    {
        if(u==-1)break;
        int c=(v>>i)&1;
        if(node[u][c^1]!=-1&&re[node[u][c^1]])
        {
            ans=(ans|(1<<i));
            u=node[u][c^1];
        }
        else u=node[u][c];
    }
    return ans;
}
int main()
{
    int T;
    scanf("%d",&T);
    while(T--)
    {
        int n;
        scanf("%d",&n);
        cnt=0;
        node[0][0]=node[0][1]=-1;
        re[0]=0;
        for(int i=1; i<=n; ++i)
            scanf("%d",&a[i]),update(a[i],1);
        int ans=0;
        for(int i=1; i<n; ++i)
        {
            update(a[i],-1);
            for(int j=i+1; j<=n; ++j)
            {
                update(a[j],-1);
                ans=max(ans,getans(a[i]+a[j]));
                update(a[j],1);
            }
            update(a[i],1);
        }
        printf("%d\n",ans);
    }
    return 0;
}
View Code

 

posted @ 2015-11-14 15:44  shuguangzw  阅读(169)  评论(0编辑  收藏  举报