求树中两个节点的最低公共祖先
给定一棵树和两个节点,求解这两个节点在树中的最低公共祖先节点。(剑指Offer)
思路:
从根节点遍历树,直到要查找的节点,保存从根节点到要查找的节点的路径。遍历两次树,即保存了根节点到要查找的两个节点的两条路径,然后求出两条路径的最后一个交点即可。
C++代码实现:
#include <iostream>
#include <vector>
#include <list>
using namespace std;
typedef struct TreeNode{
int data;
struct TreeNode *leftChild;
struct TreeNode *rightChild;
}TreeNode, *BiTree;
bool GetNodePath(TreeNode* pRoot, int data, list<BiTree> &path){
if(pRoot == NULL){
return false;
}
if(pRoot->data == data){
return true;
}
path.push_back(pRoot);
bool found = false;
if(!found){
found = GetNodePath(pRoot->leftChild, data, path);
}
if(!found){
found = GetNodePath(pRoot->rightChild, data, path);
}
if(!found){
path.pop_back();
}
return found;
}
BiTree GetLastCommonNode(list<BiTree> &path1, list<BiTree> &path2){
list<BiTree>::const_iterator i1 = path1.begin();
list<BiTree>::const_iterator i2 = path2.begin();
BiTree pLast = NULL;
for(;i1!=path1.end() && i2!=path2.end();){
if(*i1 == *i2){
pLast = *i1;
}
++i1;
++i2;
}
return pLast;
}
BiTree GetLastCommonParent(TreeNode* pRoot, int data1, int data2){
if(pRoot == NULL){
return NULL;
}
list<BiTree> path1, path2;
GetNodePath(pRoot, data1, path1);
GetNodePath(pRoot, data2, path2);
return GetLastCommonNode(path1, path2);
}
int creatTree(BiTree &T){
int data;
cin >> data;
if(data == -1){
T = NULL;
return 0;
}else{
T = (BiTree)malloc(sizeof(TreeNode));
T->data = data;
creatTree(T->leftChild);
creatTree(T->rightChild);
}
return 0;
}
int main(int argc, const char * argv[]) {
// insert code here...
BiTree T, result;
int data1, data2;
creatTree(T);
cin >> data1 >> data2;
result = GetLastCommonParent(T, data1, data2);
cout << result->data << endl;
return 0;
}