在二叉樹中找到兩個節點的最近公共祖先 高階

2021-10-23 20:25:52 字數 1766 閱讀 2005

在二叉樹中找到兩個節點的最近公共祖先(高階)

給定一棵二叉樹,多次給出這棵樹上的兩個節點 o1 和 o2,請對於每次詢問,找到 o1 和 o2 的最近公共祖先節點。

輸入描述:

第一行輸入兩個整數 n 和 root,n 表示二叉樹的總節點個數,root 表示二叉樹的根節點。

以下 n 行每行三個整數 fa,lch,rch,表示 fa 的左兒子為 lch,右兒子為 rch。(如果 lch 為 0 則表示 fa 沒有左兒子,rch同理)

第 n+2 行輸入乙個整數 m,表示詢問的次數。

以下 m 行每行兩個節點 o1 和 o2。

輸出描述:

對於每組詢問每行輸出乙個整數表示答案。

示例1輸入

8 1

1 2 3

2 4 5

4 0 0

5 0 0

3 6 7

6 0 0

7 8 0

8 0 0

44 5

5 26 8

5 8

輸出
223

1

備註:

1 ≤n

≤1000

1 \leq n \leq 1000

1≤n≤10

00 1≤m

≤106

1 \leq m \leq 10^6

1≤m≤1061≤

fa,l

ch,r

ch,r

oot,

o1,o

2≤

n1 \leq fa,lch,rch,root,o_1,o_2 \leq n

1≤fa,l

ch,r

ch,r

oot,

o1​,

o2​≤

n o 1≠

o2

o_1 \neq o_2

o1​​=

o2​題解:

建樹過程中儲存節點的父節點,每次查詢時,分別儲存每個節點到根節點的序列,最後從尾到首同時遍歷兩個序列,最後乙個相等的節點就是它們的最近公共祖先節點;

離線(提前處理所有節點對的最近公共祖先,查詢時直接返回結果就行):

處理比較麻煩,可參考書上該部分內容。。。

**:

#include

using

namespace std;

const

int n =

1010

;struct bst bst[n]

;int n, rt;

int fa, lch, rch;

int m, o1, o2;

int preo1[n]

, preo2[n]

;int n_o1, n_o2;

void

get_par

(int

&root,

int arr,

int& k)

}int

lca(

int&o1,

int&o2)

if(i <0)

return preo1[i +1]

;else

return preo2[j +1]

;}intmain

(void

)scanf

("%d"

,&m)

;while

(m--

)return0;

}

在二叉樹中找到兩個節點的最近公共祖先 I

給定一棵二叉樹的頭節點 head,以及這棵樹中的兩個節點 o1 和 o2,請返回 o1 和 o2 的最 近公共祖先節點。說明 o1和o2要麼同時都在二叉樹上,要麼同時都不在二叉樹上。後序遍歷二叉樹,假設遍歷到的當前節點為 cur。因為是後序遍歷,所以 先處理 cur 的兩棵子樹。假設處理 cur 左...

在二叉樹中找到兩個節點的最近公共祖先 再高階

在二叉樹中找到兩個節點的最近公共祖先 再高階 給定一棵二叉樹,多次給出這棵樹上的兩個節點 o1 和 o2,請對於每次詢問,找到 o1 和 o2 的最近公共祖先節點。輸入描述 第一行輸入兩個整數 n 和 root,n 表示二叉樹的總節點個數,root 表示二叉樹的根節點。以下 n 行每行三個整數 fa...

演算法實現 在二叉樹中找到兩個節點的最近公共祖先

該題目來自一次面試。在二叉樹中找到兩個節點的最近公共祖先 高階 給定一棵二叉樹,多次給出這棵樹上的兩個節點 o1 和 o2,請對於每次詢問,找到 o1 和 o2 的最近公共祖先節點。輸入描述 第一行輸入兩個整數 n 和 root,n 表示二叉樹的總節點個數,root 表示二叉樹的根節點。以下 n 行...