大致思路如下:假设所求的两个节点p,q一个位于节点node的左子树中,一个位于节点node的右子树,那么我们就可以确定,该节点node就是他们俩的最近公共祖先。。
如果节点p和q都在该节点node的同一侧,那么就去这一侧继续找,如此递归下去
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include <iostream>
#include <stack>
using namespace std;
typedef struct TREE {
int val;
TREE *left, *right;
}*BITREE;
//创建
void create(BITREE *root)
{
int val;
cin >> val;
if (val == 0) {
*root = NULL;
return;
}
else {
*root = (BITREE)malloc(sizeof(TREE));
(*root)->val = val;
create(&(*root)->left);
create(&(*root)->right);
}
}
//前序遍历
void PreOrder(BITREE *root) {
if (*root == NULL)return;
cout << (*root)->val << " ";
PreOrder(&(*root)->left);
PreOrder(&(*root)->right);
}
//求任意两个节点的最近公共祖先
BITREE *Find(BITREE *root, int p, int q) {
/*
当p与q分别在某一个节点的左右时,该节点就是所求的最近祖先
如果都在同一侧,就去找对应的子节点,递归
因此要理解本题首先要对于递归有一定的理解
*/
if (*root == NULL || (*root)->val == p || (*root)->val == q)return root;
BITREE *left = Find(&(*root)->left, p, q);
BITREE *right = Find(&(*root)->right, p, q);
if (*left && *right)return root;
if (*left)return left;
if (*right)return right;
}
int main()
{
cout << "PS:请注意输入0代表结束\n";
cout << "——————————————————————————————————————————————" << endl;
BITREE root;
root = (BITREE)malloc(sizeof(TREE));
//建树
create(&root);
//遍历
cout << "\n先序遍历的结果为:" << endl;
PreOrder(&root);
cout << "\n请输入p和q的值" << endl;
int p, q;
cin >> p >> q;
cout << "\n这两个节点的最近祖先节点对应的值为:" << endl;
cout << (*Find(&root, p, q))->val << endl;
}
如图所示我们建立一颗二叉树,对应的输出结果为