![](/img/trans.png)
[英]Python find lowest common ancestor of two nodes in a binary tree if not all of these nodes in the tree
[英]find lowest common ancestor of two Tree nodes, without reference to root?
class TreeNode {
TreeNode parent;
TreeNode left;
TreeNode right;
// other data fields omitted - not relevant
}
給定兩個節點p
和q
,如何找到最低的共同祖先? (假設它們都屬於一棵非常大的樹)
您沒有對樹根的引用。
執行此操作的最有效方法是什么? 到目前為止,我唯一的想法是
(1) 選擇一個節點 p(哪個無關緊要)
(2) 搜索p的左子樹,如果看到q,則返回p
(3) else 搜索p的右子樹,如果看到q,則返回p
(4) else 上一級到parent,搜索不包含p的子樹,如果找到q,則返回parent
(5) 否則,再上一層,重復(4)(搜索不包含該父級的子樹)
這似乎非常低效。 有什么更好的算法嗎?
您是否對允許使用的 RAM 量有極端限制? 如果沒有,我會提出這樣的建議:
visited_nodes = {} // something like a HashMap, with O(1) insert and retrieval
node1 = p
node2 = q
while True:
if node1 == null and node2 == null: // the nodes don't seem to be in same tree
return null // or failure or anything like that
if node1 is not null:
if node1 in visited_nodes: // node1 must be lowest common ancestor
return node1
else:
visited_nodes.insert(node1) // remember that we've seen this node
node1 = node1.getParent()
if node2 is not null:
if node2 in visited_nodes: // node2 must be lowest common ancestor
return node2
else:
visited_nodes.insert(node2) // remember that we've seen this node
node2 = node2.getParent()
直觀的想法如下。 我們同時從兩個節點開始。 在循環的每次迭代中,我們從兩個節點都向上一步。 每當我們看到一個節點時,我們就把它放在我們的地圖中(它應該有 O(1) 次插入和檢索/檢查它是否已經在那里)。 當我們遇到一個我們已經放在地圖中的節點時,那一定是我們的解決方案。
此代碼不應運行超過max(d_p, d_q)
次迭代,其中d_p
和d_q
分別表示p
和q
在樹中的深度級別。 如果兩個節點碰巧都非常靠近根,這將是一個很大的優勢。 這也意味着該代碼甚至適用於無限樹(而您的解決方案將陷入無限循環)。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.