-
The xor-longest Path
设 dp[x]表示根节点到 x 的路径上所有边权的 xor 值 ,显然有:
dp[x] = dp[fa[x]] ^ w(x,fa(x))
可以对树进行一次dfs,求出所有的 dp[x]
树上 x 到 y 的路径上所有边权的 xor 值结果就等于 dp[x] ^dp[y]
这是因为根据 xor 运算的性质。“x 到根”和 “y 到根”这两条路径重叠的部分,恰好抵消掉。
所以,问题就变成了从 dp[1] ~ dp[N] 这 N 个数中选出两个, xor 的值最大,可以用 Trie 树快速解决。
#include<bits/stdc++.h>
using namespace std;
const int N=1e5+10;
int ne[N<<1],e[N<<1],h[N],w[N<<1];
int son[N*32][2],idx;
int dp[N];
void add(int a,int b,int c)
{
e[idx]=b,w[idx]=c,ne[idx]=h[a],h[a]=idx++;
}
void dfs(int u,int fa,int sum)//当前节点,父节点.
{
dp[u]=sum;
for(int i=h[u];~i;i=ne[i])
{
int v=e[i];
if(v!=fa)
dfs(v,u,sum^w[i]);
}
}
void Insert(int k)
{
int p=0;
for(int i=30;~i;i--)
{
int temp=k>>i&1;
if(!son[p][temp])
son[p][temp]=++idx;
p=son[p][temp];
}
}
int Query(int k)
{
int p=0,res=0;
for(int i=30;~i;i--)
{
int temp=k>>i&1;
if(son[p][!temp])
{
res+=1<<i;
p=son[p][!temp];
}
else
p=son[p][temp];
}
return res;
}
int main()
{
int n;
cin>>n;
memset(h,-1,sizeof h);
for(int i=0;i<n-1;i++)
{
int x,y,z;
cin>>x>>y>>z;
add(x,y,z);
add(y,x,z);
}
dfs(0,-1,0);
for(int i=0;i<n;i++)
Insert(dp[i]);
int ans=0;
for(int i=0;i<n;i++)
ans=max(ans,Query(dp[i]));
cout<<ans<<endl;
return 0;
}
网友评论