說實話,和這題很有緣分。首先,這個題目給我印象很深,其次,今天在做蘑菇街實習生筆試時遇到了這個題目,所以感覺應該寫部落格,把這個題目記錄下來。
筆試時遇到的題目是:給定二叉樹中的兩個結點,尋找最低公共節點。
這是一種情況,是比較簡單的情況。
這種情況就相當於求兩條鍊錶的公共節點。求解很簡單,先把遍歷把兩條鍊錶的長度求得。加入list1長a,list2長為b,求則a、b中的較大者先從頭遍歷走a-b步,然後兩條鍊錶同時遍歷,第乙個相同的節點是最低公父節點。
這種情況難點。所謂兩個結點的公共祖先,指的是兩個結點都出現在現在某個節點的子樹中。我們可以從根結點開始遍歷樹,每遍歷到乙個結點時,判斷兩個輸入結點是不是在它的子樹中。如果在子樹中,則分別遍歷它的所有子結點,並判斷兩個輸入結點是不是在它們的子樹中。這樣一直向下找,直到找到乙個結點,它自己的子樹同時包含兩個輸入的子結點而它的子結點卻沒有,那麼該結點就是最低的公共祖先。
我在這次筆試就是採用這種解法。
typedef
struct treenode treenode;
/* 檢視root結點的子樹是否包含distri */
bool hasnode(treenode *root, treenode *distri)
if (root->val == distri->val)
return hasnode(root->left, distri) || hasnode(root->right, distri);
}treenode *commomfather(treenode *root, treenode *node1, treenode *node2)else
if(null != commomfather(root->left, node1, node2))else
if ((null != commomfather(root->left, node1, node2))
return null;
}
當然我並沒有檢驗,這是憑記憶回想自己在考場寫的**。
上一種方法很明顯,我們對同一結點都會重複遍歷很多次,我們尋求一種更快的解法。
《劍指offer》提供了一種思路:
使用輔助記憶體,用兩個鍊錶分別儲存從根結點到輸入兩個結點的路徑,然後把問題轉換為兩個鍊錶的最後公共結點。這種解法為了得到根結點開始到輸入的兩個結點的兩條路徑,需要兩次遍歷樹,每一次遍歷需要o(n).得到兩條路徑長度最差是o(n),通常情況下兩條路徑長度是o(logn).
/* 獲取root到node的path */
bool getnodepath(treenode *root, treenode *node, list
&path)
path.push_back(root);
bool found = false;
vector
::iterator it = root->m_vchildren.begin();
while (!found && i < root->m_vchildren.end())
if (!found)
return found;
}/* 獲取相同結點 */
treenode *getlastcommonnode(const
list
&path1, const
list
&path2)
iterator1++;
iterator2++;
} return plast;
}treenode *getlastcommonparent(treenode *root, treenode *node1, treenode *node2)
list
path1;
getnodepath(root, node1, path1);
list
path2;
getnodepath(root, node2, path2);
return getlastcommonnode(path1, path2);
}
好了,完 劍指Offer 68 樹中兩個結點的最低公共祖先
給出乙個二叉樹,輸入兩個樹節點,求它們的最低公共祖先。乙個樹節點的祖先節點包括它本身。注意 輸入的二叉樹不為空 輸入的兩個節點一定不為空,且是二叉樹中的節點 解法一,使用遞迴,若兩個樹節點在根節點的左右子樹上,則公共節點為根節點 若兩個樹節點都在某一子樹上,則公共節點在該子樹上。這個方法遞迴都要查詢...
劍指offer 樹中兩個節點的最低公共祖先
與 劍指offer 得到從根節點開始到輸入的兩個結點的兩條,需要遍歷兩次樹,每遍歷一次的時間複雜度是o n 得到的兩條路徑的長度在最差情況時是o n 通常情況下兩條路徑的長度是o logn include include include using namespace std struct tree...
劍指offer 樹中兩個節點的最低公共祖先
對於這個問題不同的條件可以有不同的解法 binarytreenode getlastcommonparent binarytreenode proot,binarytreenode pnode1,binarytreenode pnode2 普通二叉樹,沒有parent指標 非遞迴的解法 1.獲取結點...