預處理:通過dfs遍歷,記錄每個節點到根節點的距離dist[u],深度d[u]
init()求出樹上每個節點u的2^i祖先p[u][i]
求最近公共祖先,根據兩個節點的的深度,如不同,向上調整深度大的節點,使得兩個節點在同一層上,如果正好是祖先結束,否則,將連個節點同時上移,查詢最近公共祖先。
void dfs(int u)}
i的2^j祖先就是i的(2^(j-1))祖先的2^(j-1)祖先:
void init()}a=p[a][0];//這時a的father就是lca
}return a;
}
明明倍增的時間複雜度是o(nlogn)的,tarjan的時間複雜度是o(n)的,但是tarjan問什麼比倍增慢那麼多啊?
倍增法求 LCA
預處理 通過dfs遍歷,記錄每個節點到根節點的距離dist u 深度d u 並求出樹上每個節點i的2 j祖先f i j 求最近公共祖先,根據兩個節點的的深度,如不同,向上調整深度大的節點,使得兩個節點在同一層上,如果正好是祖先結束,否則,將連個節點同時上移,查詢最近公共祖先。include incl...
倍增法求lca
f i j 表示從i這個節點出發,向上走2 j步到達的點 超過了最大深度就返回0 那麼顯然有 因為相當於是從i點先向上走2 j 1 步,再走2 j 1 步。等價於一共走2 j步。然後求lca就是 先把深度大的那個點往上跳,使兩個點的深度相同。對應的 for int i 18 i 0 i if dep...
倍增法求LCA
解決的問題 在一棵樹上求u,v的最近公共祖先。思路 預處理parents陣列和depth陣列,首先使u,v深度相同,一起向上迭代,直至找到相同父節點 倍增法求lca include include include includeusing namespace std define n 100010 ...