CF983E NN country 題解
題意
給定一棵樹和若干條路線,每條路線相當(dāng)于 ?之間的路徑,途徑路徑上的每個(gè)點(diǎn)。
給出若干個(gè)詢問,每次詢問從 ?到
?至少需要利用幾條路線。
Solution
對(duì)于鏈,考慮貪心,對(duì)于每一個(gè)點(diǎn) ?跳到能到達(dá)的最遠(yuǎn)的點(diǎn)?,容易想到下一步應(yīng)當(dāng)是跳到
,故考慮倍增優(yōu)化這個(gè)不斷往前跳的過程。定義
?為點(diǎn) i 跳
?步能到達(dá)的最遠(yuǎn)節(jié)點(diǎn),可以用
?復(fù)雜度的時(shí)間來處理出?
數(shù)組。
考慮樹上的兩個(gè)點(diǎn),對(duì)于 ?是?
?的祖先節(jié)點(diǎn)(
?為
?祖先節(jié)點(diǎn)時(shí)同理)的情況,同鏈上情況處理。
對(duì)于兩個(gè)點(diǎn)分別不是對(duì)方父親節(jié)點(diǎn)的情況,考慮將問題拆分為??到?
?和?
?到
?兩個(gè)問題處理。令
為?
?跳到
?的最小步數(shù),
?為?
跳到
?的最小步數(shù),
?為?
向上跳
?步到達(dá)的深度最淺的節(jié)點(diǎn),即跳到
?的前一個(gè)節(jié)點(diǎn), 同理。考慮兩種情況:
有一條路線同時(shí)經(jīng)過?
?和
;
不存在一條路線同時(shí)經(jīng)過
?和
。
對(duì)于第二種情況,答案即為 ,對(duì)于第一種情況,答案為 。問題轉(zhuǎn)化為如何維護(hù)是否存在一條路線經(jīng)過兩個(gè)點(diǎn)。
發(fā)現(xiàn)對(duì)于一個(gè)節(jié)點(diǎn) ,只要
的子樹中存在一個(gè)點(diǎn),使得存在一條從其出發(fā)的路徑在
的子樹中結(jié)束,則存在一條路徑同時(shí)經(jīng)過
和
。考慮通過 dfs 序轉(zhuǎn)化為區(qū)間問題,令
?為節(jié)點(diǎn)
?的子樹大小,則問題進(jìn)一步轉(zhuǎn)化為詢問是否存在一條路徑
?使得
。考慮二維數(shù)點(diǎn),即查詢平面上矩形
?是否有點(diǎn)。將詢問離線排序并用樹狀數(shù)組維護(hù)即可。
有個(gè)小細(xì)節(jié):由于 ?和?
在此題中是等價(jià)的,故在插入點(diǎn)時(shí)都應(yīng)插入,否則可能會(huì)統(tǒng)計(jì)不到這個(gè)點(diǎn)。
其他具體實(shí)現(xiàn)細(xì)節(jié)見代碼,以及由于我不會(huì)倍增求 lca,所以寫了個(gè)樹剖。
總時(shí)間復(fù)雜度應(yīng)該是 ?的,但是有巨大常數(shù),可以通過本題。
code