题目描述
请设计一个算法,寻找二叉树中指定结点的下一个结点(即中序遍历的后继)。
给定树的根结点指针TreeNode* root和结点的值int p,请返回值为p的结点的后继结点的值。保证结点的值大于等于零小于等于100000且没有重复值,若不存在后继返回-1。
/*
struct TreeNode {
int val;
struct TreeNode *left;
struct TreeNode *right;
TreeNode(int x) :
val(x), left(NULL), right(NULL) {
}
};*/
class Successor {
public:
vector<int> res;
int findSucc(TreeNode* root, int p) {
midindex(root);
int i;
for (i = 0; i < res.size(); i++)
{
if (res[i] == p)
break;
}
if (i == res.size() - 1)
return -1;
else
return res[i + 1];
}
void midindex(TreeNode* root)
{
if (root->left != NULL)
midindex(root->left);
res.push_back(root->val);
if (root->right != NULL)
midindex(root->right);
}
};
题目分析:
要寻找中序遍历的某个节点的下一个节点,肯定是要通过中序遍历实现的,题目中明确告诉我们节点的值没有重复,所以只要在中序遍历的过程中,某个节点的值等于p,则告诉递归者下一个要遍历的节点便是我们要找的节点,这个需要有个信号在多次递归之间进行传递消息,c++里用引用完全可以实现,只需要传递一个bool类型的引用便可。
class Successor {
public:
int findSucc(TreeNode* root, int p) {
// write code here
bool sign=0;
return findSucc1(root,p,sign);
}
int findSucc1(TreeNode* root,int p,bool &sign)
{
if(root==NULL)
return -1;
int left=findSucc1(root->left,p,sign);
if(left!=-1)
return left;
if(sign==true)
return root->val;
if(root->val==p)
sign=true;
return findSucc1(root->right,p,sign);
}
};
class Successor {
public:
int findSucc(TreeNode* root, int p) {
bool isFound = false;
stack<TreeNode*> s;
TreeNode* cur = root;
while(cur || !s.empty()){
while(cur){
s.push(cur);
cur = cur->left;
}
if(!s.empty()){
cur = s.top();
s.pop();
if(isFound) return cur->val;
else if(cur->val==p) isFound = true;
cur = cur->right;
}
}
return -1;
}
};