LCA(最近公共祖先) 的兩種求解方法

2021-10-02 13:56:09 字數 923 閱讀 4922

lca,即最近公共祖先,是圖論中關於樹的乙個非常重要的定義。

在一棵樹中,若節點z既是節點x的祖先節點,又是節點y的祖先節點,那麼稱節點z是節點x和y的公共祖先節點。

兩種解法: 

其實還有第三種方法,可以用tarjan演算法優化第一種情況,但是前提條件是需要將詢問離線,演算法時間複雜度是

// lca o(nlog(n))

#include #pragma warning (disable:6031)

#define mem(a, b) memset(a, b, sizeof a)

using namespace std;

const int n = 310;

int head[n], nex[n], to[n];

int f[n][n]; //倍增思想,依然用不到n * n的區間,大概是n * (log(n) / log(2))的大小就夠了

int cnt;

int d[n];

typedef struct build_tree

void init()

void add(int x, int y)

}bt;

int n; // 樹上n個點,n - 1條邊

void dfs(int x, int depth)

}int ans(int x, int y)

if (x == y)return x;

for (int i = log(n) / log(2); i >= 0; i--)

return f[x][0];

}int main()

int tt = log(n) / log(2);

for (int i = 1; i <= tt; i++)

} return 0;

}

LCA 最近公共祖先的四種解法

給定一棵有根多叉樹,請求出指定兩個點直接最近的公共祖先。樹的構造 舉個栗子 尤拉序 儲存第一次出現的位置 使用鏈式前向星儲存樹的結構,首先求一棵樹的尤拉序,然後根據兩點的公共祖先就是尤拉序中 第一次出現時 兩點位置區間內的深度最小點,這一定理轉化成rmq最小問題,使用st表時注意log2的複雜度比較...

最近公共祖先 LCA 的Tarjan演算法

lca t,u,v 在有根樹t中,詢問乙個距離根最遠的結點x,使得x同時為結點u v的祖先 lca問題可以用樸素的dfs方法解決,但是時間複雜度就很高了,這裡介紹一種高階一點的解決lca問題的tarjan演算法。tarjan演算法是由robert tarjan在1979年發現的一種高效的離線演算法,...

節點的最近公共祖先(LCA倍增法)

樹是一種很常見的資料結構。現在蒜頭君面臨乙個問題,在乙個有 n 個節點的樹上,節點編號分別是1 n。蒜頭想知道一些節點之間的最近公共祖先是那些節點。輸入格式 第一行輸入乙個整數 n 2 n 10,000 表示樹上有 n 個節點。接下來的 n 1 行,每行輸入倆個整數 a,b 1 a,b n 代表節點...