题目描述
给定一棵二叉搜索树,请找出其中的第k小的结点。例如,(5,3,7,2,4,6,8)中,按结点数值大小顺序第三小结点的值为4。
解题思路
首先,二叉搜索树有一个很好的特性,任意一个结点必大于其左子树的所有结点,必小于等于其右子树的所有结点。如果使用中序遍历二叉搜索树,那么结果会按数值从小到大的顺序输出。
<图>
例如上图就是一棵二叉搜索树。中序遍历上图的二叉搜索树,输出结果为:1,3,4,6,7,8,10,13,14。
所以自然地我们就产生了一个解决方法,就是使用中序遍历二叉搜索树,记录输出个数,如果输出个数等于目标 k,则返回该结点即可。
这里使用非递归的方法实现中序遍历,以便记录输出个数。使用栈来存储结点,先扫描根结点的所有左结点,并将它们放进栈,直至左结点为空,然后取出栈顶结点,访问栈顶结点,再扫描该结点的右结点,将其进栈,再扫描这个右结点的所有左结点并进栈,如此继续,直到栈空。
(PS:博客《二叉树的中序遍历非递归算法》中用图展示了中序遍历的非递归算法,比较直观。另一篇 博客 则展示了二叉树的三种遍历方法递归及非递归的实现代码。)
实现代码:
/*
struct TreeNode {
int val;
struct TreeNode *left;
struct TreeNode *right;
TreeNode(int x) :
val(x), left(NULL), right(NULL) {
}
};
*/
class Solution {
public:
TreeNode* KthNode(TreeNode* pRoot, int k)
{
if(!pRoot){
return NULL;
}
stack<TreeNode*> nodes;
TreeNode* p = pRoot;
int count = 0;
while(p|| !nodes.empty()){
if(p){
nodes.push(p);
p = p->left;
}else{
p = nodes.top();
count++;
if(count==k){
break;
}
nodes.pop();
p = p->right;
}
}
return p;
}
};
参考链接:
1.https://blog.csdn.net/billy1900/article/details/86229656
2.https://www.jianshu.com/p/2b4a58bf48ad
来源:CSDN
作者:名字要够长系列
链接:https://blog.csdn.net/qq_36641919/article/details/104213563