最長パスXOR演算

最長パスXOR演算

そこに、N個のノードのツリー与えられる設定([I] [J wは\を ] \)は右端からの距離であり、右側のパスイソブチルまたは全ての側面上にあるI、J、の間のパスを定義しますそして、あなたは、任意の2点を選択した2点間の経路距離を最小化し、最大値を取得する\(1≤n≤100000\)

ソリューション

ツリーの問題、全く根の根はより良い研究、そこになっていない、通常設定その後、ルートノードへの各ノードのために維持される\(Sを[I] \)排他的なルートノードへの重み経路または点Iを表します。これは再びそれを維持することができ、DFS、私は余分をアピールしません。

このとき、任意の2点のためにi、jは距離の間となることを見出した\(W [I] \ウェッジW [J] \) 排他的論理和結果の同じ数の同じ数が0であるため(\ W [i]は\ウェッジ[J] \)wは、正確ためこの種のルートノードに共通の祖先からI、Jを除去し、残りは自然距離Iのjからです。

そこで問題は、設定されてしまう(\ {[i]はワット\ \ \}) 2つの数値を選択し、かつ高いから文字列01として、限り、我々はトライ木を維持するように、これらの数字を明らかに、彼らの排他的論理和を最大化その後、低トライへの挿入、および非ゼロの数の数をすることができ、この1を作るために、トップダウンからトライ木から各番号を選択してみてください。

参照コード:

#include <iostream>
#include <cstdio>
#define il inline
#define ri register
#define Size 100050
using namespace std;
struct point{
    point *next;int to,w;
}*pt,*head[Size];
bool is[Size];
int dis[Size],trie[Size*31][2],tot;
void dfs(int);
il int ask(int);
il void read(int&),
    link(int,int,int),
    insert(int);
template<class free>
il free Max(free,free);
int main(){
    int n,ans(0);read(n);
    for(int i(1),u,v,w;i<n;++i)
        read(u),read(v),read(w),
            link(u,v,w),link(v,u,w);dfs(0);
    for(int i(1);i<=n;++i)
        ans=Max(ans,ask(dis[i]));
    printf("%d",ans);
    return 0;
}
template<class free>
il free Max(free a,free b){
    return a>b?a:b;
}
il int ask(int x){
    int ans(0),p(0);
    for(int i(30);i>=0;--i)
        if(trie[p][x>>i&1^1])
            p=trie[p][x>>i&1^1],
                ans|=1<<i;
        else p=trie[p][x>>i&1];
    return ans;
}
il void insert(int x){int p(0);
    for(int i(30);i>=0;--i){
        if(!trie[p][x>>i&1])
            trie[p][x>>i&1]=++tot;
        p=trie[p][x>>i&1];
    }
}
void dfs(int x){is[x]|=true,insert(dis[x]);
    for(point *i(head[x]);i!=NULL;i=i->next){
        if(is[i->to])continue;
        dis[i->to]=dis[x]^i->w,dfs(i->to);
    }
}
il void link(int u,int v,int w){
    pt=new point{head[u],v,w},head[u]=pt;
}
il void read(int &x){
    x^=x;ri char c;while(c=getchar(),c<'0'||c>'9');
    while(c>='0'&&c<='9')x=(x<<1)+(x<<3)+(c^48),c=getchar();
}

おすすめ

転載: www.cnblogs.com/a1b3c7d9/p/11248071.html