hdu 6191 Query on A Tree(dfs序+可持久化字典树)

题目链接:hdu 6191 Query on A Tree

题意:

给你一棵树,每个节点有一个值,现在有q个询问,每个询问 询问一个u x,问以u为根的子树中,找一个节点,使得这个节点的值与x异或的值最大,输出那个最大的值。

题解:

dfs序和一棵可持久化字典树就搞定了。

 1 #include<bits/stdc++.h>
 2 #define mst(a,b) memset(a,b,sizeof(a))
 3 #define F(i,a,b) for(int i=a;i<=b;++i)
 4 using namespace std;
 5 
 6 const int N=1e5+7;
 7 struct Node{int son[2],cnt;}ch[N*40];
 8 int root[N],cnt,n,q,val[N],x,idx,in[N],out[N],rev[N];
 9 vector<int>g[N];
10 
11 void ins(int &x,int y,int v,int i=31)
12 {
13     ch[x=++cnt]=ch[y],ch[x].cnt++;
14     if(i<0)return;
15     int now=(v>>i)&1;
16     ins(ch[x].son[now],ch[y].son[now],v,i-1);
17 }
18 
19 int ask_xor(int x,int y,int v,int i=31,int ans=0)
20 {
21     if(i<0)return ans;
22     int now=(v>>i)&1;
23     if(ch[ch[y].son[now^1]].cnt-ch[ch[x].son[now^1]].cnt>0)
24         return ask_xor(ch[x].son[now^1],ch[y].son[now^1],v,i-1,ans+(1<<i));
25     else return ask_xor(ch[x].son[now],ch[y].son[now],v,i-1,ans);
26 }
27 
28 int ask(int l,int r,int x)
29 {
30     printf("%d
",ask_xor(root[l-1],root[r],x));
31 }
32 
33 void dfs(int x)
34 {
35     in[x]=++idx,rev[idx]=x;
36     for(auto &it:g[x])dfs(it);
37     out[x]=idx;
38 }
39 
40 int main(){
41     while(~scanf("%d%d",&n,&q))
42     {
43         cnt=0;F(i,1,n)g[i].clear();
44         F(i,1,n)scanf("%d",val+i);
45         F(i,2,n)scanf("%d",&x),g[x].push_back(i);
46         idx=0,dfs(1);
47         F(i,1,idx)ins(root[i],root[i-1],val[rev[i]]);
48         F(i,1,q)
49         {
50             int a,b;
51             scanf("%d%d",&a,&b);
52             ask(in[a],out[a],b);
53         }
54     }
55     return 0;
56 }
View Code
原文地址:https://www.cnblogs.com/bin-gege/p/7462496.html