競プロ覚書

思考整理

ABC201-E Xor Distances

本番で解けず。重みを桁ごとに分解するという発想がなかった

【問題】

重み付き木が与えられる。

dist(i, j) = iからjへの最短パスに含まれる辺すべての重みのXOR

すべてのi ,j(i<j)についてdistの総和を求めよ

【忘れがちな知識】

総和は桁ごとに独立して足し合わせられる

例:123+789 = 1*10^2+7*10^2+2*10^1+8*10^1+3^10^0+9*10^0

【典型ポイント】

XOR => 桁ごとに考える

【方針】

 

愚直にdist(i,j)を全列挙としようとすると最低でもO(N^2)となり、全然間に合わない。

また、それぞれのdist(i, j)も高速に求める必要がある。

 

・2点間の最短パスを高速に求める

適当な根をrとして木を探索し、dist(r, i)を求める。

jこのとき、dist(i, j) = dist(r, i) ^ dist(r, j) となる(下図参照)

ので、任意のdist(i, j)を前計算O(N), 処理O(1)で求められる。

f:id:pm4:20210518203102p:plain
これで各distを高速に求めることはできたが、まだO(N^2)かかる。

・distを桁ごとに求める

dist(i, j)はXOR演算を繰り返すので、桁ごとに独立して考えることができる。

 こうすると辺の重みとdist(i, j)の各桁は0か1の2通りになる。

各桁のdist(i, j)をdk(i, j)とすると

任意のi, j(i<j)を選んだ時、dk(i, j)が1になるのはdk(r,i) != dk(r, j)のときなので、

dk(i, j) = 1 と dk(r, i) != dk(r, j) が等しい。

よって、各桁においてdist(i, j) = 1 となる組み合わせの数は、1~nの各頂点において

count(dk=0) * count(dk=1) 

となる。(2種類のボールの山から2個を選んだ時に色が異なる組み合わせの数と同じ)