題目鏈接
思路:求最大異或我們考慮01字典樹,但是在樹上怎麼建呢?我們考慮一下樹上一點u,點u到其他點的最大異或和路徑可以通過邊dfs邊建字典樹的方式進行。
#include<iostream>
#include<cstdio>
#include<vector>
using namespace std;
const int maxn=2e5+5;
typedef long long ll;
vector<pair<int,int> >g[maxn];
ll tree[maxn*32][2],tot,ans;
void insert(ll x)
{
int u=0;
for(int i=30;i>=0;--i)
{
int t=(((1LL<<i)&x)?1:0);
if(!tree[u][t]) tree[u][t]=++tot;
u=tree[u][t];
}
}
ll query(ll x)
{
int u=0;
ll res=0;
for(int i=30;i>=0;--i)
{
int t=(((1LL<<i)&x)?1:0);
if(tree[u][t^1]) u=tree[u][t^1],res+=(1LL<<i);
else u=tree[u][t];
}
return res;
}
void dfs(int x,int fa,ll sum)
{
ans=max(ans,query(sum));
for(int i=0;i<g[x].size();++i)
{
int to=g[x][i].first;
if(to==fa) continue;
ll t=sum^g[x][i].second;
insert(t);
dfs(to,x,t);
}
}
int main()
{
int n,u,v,w;
scanf("%d",&n);
for(int i=0;i<n-1;++i)
{
scanf("%d %d %d",&u,&v,&w);
g[u].push_back({v,w});
g[v].push_back({u,w});
}
insert(0);
dfs(1,-1,0);
printf("%lld\n",ans);
}