BZOJ 1954: Pku3764 The xor-longest Path(01trie)
求树上最长异或路径.
根据异或的性质,我们知道a^a=0,那么a^b^b^c=a^c;
所以我们随便找个点做根,然后dfs出每个点到根的异或路径长num[i],对于任意两点有两种情况,当根是他们的LCA时,那么两点异或路径和就直接是num[i]^num[j],不是LCA时,由于两条路径都包含了LCA到根的路径,两次异或抵消掉了,所以证得任意两点异或路径和为num[i]^num[j];
所以把num[i]扔到trie里搞一搞就行了...
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
1 #include <iostream> 2 #include <cstdio> 3 #include <cstring> 4 #include <algorithm> 5 #include <cmath> 6 #include <queue> 7 #include <map> 8 #define ll long long 9 #define out(a) printf("%d",a) 10 #define writeln printf("\n") 11 const int N=1e5+50; 12 const int MOD=1e9+7; 13 using namespace std; 14 int n; 15 int x,y,z; 16 int st,tot=1,ans=-23333333; 17 int head[N],c[N]; 18 int trie[N*31][2]; 19 bool vis[N]; 20 struct edge 21 { 22 int to,nxt,cost; 23 }edge[N<<1]; 24 void add(int x,int y,int z) 25 { 26 edge[++tot].to=y; 27 edge[tot].cost=z; 28 edge[tot].nxt=head[x]; 29 head[x]=tot; 30 } 31 int read() 32 { 33 int s=0,t=1; char c; 34 while (c<'0'||c>'9'){if (c=='-') t=-1; c=getchar();} 35 while (c>='0'&&c<='9'){s=s*10+c-'0'; c=getchar();} 36 return s*t; 37 } 38 ll readl() 39 { 40 ll s=0,t=1; char c; 41 while (c<'0'||c>'9'){if (c=='-') t=-1; c=getchar();} 42 while (c>='0'&&c<='9'){s=s*10+c-'0'; c=getchar();} 43 return s*t; 44 } 45 void dfs(int x) 46 { 47 int y; 48 for (int i=head[x];i;i=edge[i].nxt){ 49 y=edge[i].to; 50 if (!vis[y]){ 51 vis[y]=true; 52 c[y]=c[x]^edge[i].cost; 53 dfs(y); 54 } 55 } 56 } 57 void insert(int x) 58 { 59 int u=1; 60 for (int i=31;i>=0;i--){ 61 int c=((1<<i)&x)>0; 62 if (!trie[u][c]) trie[u][c]=++tot; 63 u=trie[u][c]; 64 } 65 } 66 int find(int x) 67 { 68 int u=1; 69 int res=0; 70 for (int i=31;i>=0;i--){ 71 int c=((1<<i)&x)>0; 72 if (trie[u][1-c]) u=trie[u][1-c],res+=(1<<i); 73 else u=trie[u][c]; 74 } 75 return res; 76 } 77 int main() 78 { 79 n=read(); memset(vis,false,sizeof(vis)); 80 for (int i=1;i<n;i++){ 81 x=read(),y=read(),z=read(); 82 add(x,y,z); add(y,x,z); 83 if (i==1) st=x; 84 } 85 dfs(st); 86 for (int i=1;i<=n;i++) 87 if (c[i]) { 88 ans=max(ans,c[i]); 89 ans=max(ans,find(c[i])); 90 insert(c[i]); 91 } 92 out(ans); 93 return 0; 94 } 95