力扣高频|算法面试题汇总(七):树

力扣高频|算法面试题汇总(一):开始之前
力扣高频|算法面试题汇总(二):字符串
力扣高频|算法面试题汇总(三):数组
力扣高频|算法面试题汇总(四):堆、栈与队列
力扣高频|算法面试题汇总(五):链表
力扣高频|算法面试题汇总(六):哈希与映射
力扣高频|算法面试题汇总(七):树
力扣高频|算法面试题汇总(八):排序与检索
力扣高频|算法面试题汇总(九):动态规划
力扣高频|算法面试题汇总(十):图论
力扣高频|算法面试题汇总(十一):数学&位运算

力扣高频|算法面试题汇总(七):树

力扣链接
目录:

  • 1.二叉搜索树中第K小的元素
  • 2.二叉树的最近公共祖先
  • 3.二叉树的序列化与反序列化
  • 4.天际线问题

1.二叉搜索树中第K小的元素

给定一个二叉搜索树,编写一个函数 kthSmallest 来查找其中第 k 个最小的元素。
说明:
你可以假设 k 总是有效的,1 ≤ k ≤ 二叉搜索树元素个数。
示例 1:
输入: root = [3,1,4,null,2], k = 1
3
/
1 4

2
输出: 1
进阶:
如果二叉搜索树经常被修改(插入/删除操作)并且你需要频繁地查找第 k 小的值,你将如何优化 kthSmallest 函数?

思路
这题剑指offer中做过,详见:剑指offer|解析和答案(C++/Python) (五)上:二叉搜索树的第k个节点
就是通过中序遍历查找。
C++

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
 * };
 */
class Solution {
   
public:
    int kthSmallest(TreeNode* root, int k) {
        
        // 中序遍历获得二叉搜索树的第k个节点
        TreeNode* pNode =  kthSmallestCore(root, k);
        return pNode->val;
    }
	TreeNode* kthSmallestCore(TreeNode* pRoot,  int& k){
   
		TreeNode* target = NULL;
		if(pRoot->left != NULL)//遍历左子树
			target = kthSmallestCore(pRoot->left, k);
		if(target == NULL){
   
			if(k == 1)//表示已经到第k小的节点了
				target = pRoot;
			k--;
		}
		//target = NULL 表示没有找到
		//开始遍历右子树
		if(target == NULL && pRoot->right != NULL){
   
			target = kthSmallestCore(pRoot->right, k);
		}
		return target;
	}
};

官方的极简写法:

class Solution:
    def kthSmallest(self, root, k):
        """
        :type root: TreeNode
        :type k: int
        :rtype: int
        """
        def inorder(r):
            return inorder(r.left) + [r.val] + inorder(r.right) if r else []
        return inorder(root)[k - 1]

思路2:
参考官方思路,进行迭代加速。
时间复杂度:O(H+k),其中 HH 指的是树的高度,由于我们开始遍历之前,要先向下达到叶,当树是一个平衡树时:复杂度为 O(logN+k)。当树是一个不平衡树时:复杂度为 O(N+k),此时所有的节点都在左子树。
空间复杂度:O(H+k)。当树是一个平衡树时:O(logN+k)。当树是一个非平衡树时:O(N+k)。

在这里插入图片描述

C++

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
 * };
 */
class Solution {
   
public:
    int kthSmallest(TreeNode* root, int k) {
        
        stack<TreeNode*> s;
        while(1){
   
            while(root){
   
                s.push(root);
                root = root->left;
            }
            root = s.top();
            s.pop();
            --k;
            if(k == 0)
                return root->val;
            root = root->right;
        }
    }

};

Python:

# Definition for a binary tree node.
# class TreeNode:
#     def __init__(self, x):
#         self.val = x
#         self.left = None
#         self.right = None

class Solution:
    def kthSmallest(self, root: TreeNode, k: int) -> int:
        stack = []
        while True:
            while root:
                stack.append(root)
                root = root.left
            
            root = stack[-1]
            stack.pop()
            k -= 1
            if not k:
                
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值