leetcode--二叉搜索树中第K小的元素

leetcode地址:二叉搜索树中第K小的元素
给定一个二叉搜索树的根节点 root ,和一个整数 k ,请你设计一个算法查找其中第 k 小的元素(从 1 开始计数)。

示例 1:
在这里插入图片描述

输入:root = [3,1,4,null,2], k = 1
输出:1
示例 2:

在这里插入图片描述

输入:root = [5,3,6,2,4,null,null,1], k = 3
输出:3

提示:
树中的节点数为 n 。
1 <= k <= n <= 104
0 <= Node.val <= 104

实现思路

在二叉搜索树(BST)中查找第 k 小的元素。二叉搜索树的特点是对于每个节点,左子树中的所有节点值小于该节点值,右子树中的所有节点值大于该节点值。利用这一性质,我们可以通过中序遍历(in-order traversal)来得到一个有序的元素列表,然后查找第 k 小的元素。

中序遍历
中序遍历(in-order traversal)是指先遍历左子树,再访问根节点,最后遍历右子树。对于二叉搜索树,中序遍历会按顺序访问所有节点,得到一个递增的序列。
记录遍历过程
使用一个变量来记录当前访问到的节点数,当这个计数器等于 k 时,当前节点即为第 k 小的元素。
递归或迭代
我们可以使用递归或迭代的方法来实现中序遍历。

递归实现

# 定义二叉树节点类
class TreeNode:
    def __init__(self, val=0, left=None, right=None):
        self.val = val
        self.left = left
        self.right = right

# 查找第k小元素的函数
def kthSmallest(root: TreeNode, k: int) -> int:
    def inOrderTraversal(node):
        if not node:
            return []

        # 递归遍历左子树
        left = inOrderTraversal(node.left)
        
        # 访问当前节点
        current = [node.val]
        
        # 递归遍历右子树
        right = inOrderTraversal(node.right)
        
        return left + current + right

    # 获取中序遍历结果
    result = inOrderTraversal(root)
    
    # 返回第k小的元素
    return result[k - 1]

# 测试示例
if __name__ == "__main__":
    # 创建测试二叉搜索树
    #       3
    #      / \
    #     1   4
    #      \
    #       2
    root = TreeNode(3)
    root.left = TreeNode(1)
    root.right = TreeNode(4)
    root.left.right = TreeNode(2)
    
    k = 1
    print(f"第{k}小的元素: {kthSmallest(root, k)}")  # 应该输出1

迭代实现

# 定义二叉树节点类
class TreeNode:
    def __init__(self, val=0, left=None, right=None):
        self.val = val
        self.left = left
        self.right = right

# 查找第k小元素的函数
def kthSmallest(root: TreeNode, k: int) -> int:
    stack = []
    while True:
        # 左子树遍历
        while root:
            stack.append(root)
            root = root.left
        root = stack.pop()
        k -= 1
        # 当计数器等于0时,返回当前节点的值
        if k == 0:
            return root.val
        # 右子树遍历
        root = root.right

# 测试示例
if __name__ == "__main__":
    # 创建测试二叉搜索树
    #       3
    #      / \
    #     1   4
    #      \
    #       2
    root = TreeNode(3)
    root.left = TreeNode(1)
    root.right = TreeNode(4)
    root.left.right = TreeNode(2)
    
    k = 1
    print(f"第{k}小的元素: {kthSmallest(root, k)}")  # 应该输出1

Go实现

递归实现

package main

import "fmt"

// TreeNode 定义二叉树节点
type TreeNode struct {
	Val   int
	Left  *TreeNode
	Right *TreeNode
}

// kthSmallest 递归查找二叉搜索树中的第k小元素
func kthSmallest(root *TreeNode, k int) int {
	var inOrder func(node *TreeNode) []int
	inOrder = func(node *TreeNode) []int {
		if node == nil {
			return []int{}
		}
		left := inOrder(node.Left)
		current := []int{node.Val}
		right := inOrder(node.Right)
		return append(append(left, current...), right...)
	}

	result := inOrder(root)
	return result[k-1]
}

// 测试示例
func main() {
	// 创建测试二叉搜索树
	//       3
	//      / \
	//     1   4
	//      \
	//       2
	root := &TreeNode{Val: 3}
	root.Left = &TreeNode{Val: 1}
	root.Right = &TreeNode{Val: 4}
	root.Left.Right = &TreeNode{Val: 2}

	k := 1
	fmt.Printf("第%d小的元素: %d\n", k, kthSmallest(root, k)) // 应该输出1
}

迭代实现

package main

import "fmt"

// TreeNode 定义二叉树节点
type TreeNode struct {
	Val   int
	Left  *TreeNode
	Right *TreeNode
}

// kthSmallest 迭代查找二叉搜索树中的第k小元素
func kthSmallest(root *TreeNode, k int) int {
	stack := []*TreeNode{}
	current := root

	for current != nil || len(stack) > 0 {
		for current != nil {
			stack = append(stack, current)
			current = current.Left
		}
		current = stack[len(stack)-1]
		stack = stack[:len(stack)-1]
		k--
		if k == 0 {
			return current.Val
		}
		current = current.Right
	}
	return -1 // 如果树中没有第k小的元素
}

// 测试示例
func main() {
	// 创建测试二叉搜索树
	//       3
	//      / \
	//     1   4
	//      \
	//       2
	root := &TreeNode{Val: 3}
	root.Left = &TreeNode{Val: 1}
	root.Right = &TreeNode{Val: 4}
	root.Left.Right = &TreeNode{Val: 2}

	k := 1
	fmt.Printf("第%d小的元素: %d\n", k, kthSmallest(root, k)) // 应该输出1
}

Kotlin实现

递归实现

// 定义二叉树节点类
class TreeNode(var `val`: Int) {
    var left: TreeNode? = null
    var right: TreeNode? = null
}

// 查找第k小元素的函数
fun kthSmallest(root: TreeNode?, k: Int): Int {
    // 中序遍历函数
    fun inOrderTraversal(node: TreeNode?): List<Int> {
        if (node == null) return listOf()
        
        val left = inOrderTraversal(node.left)
        val current = listOf(node.`val`)
        val right = inOrderTraversal(node.right)
        
        return left + current + right
    }
    
    val result = inOrderTraversal(root)
    return result[k - 1]
}

// 测试示例
fun main() {
    // 创建测试二叉搜索树
    //       3
    //      / \
    //     1   4
    //      \
    //       2
    val root = TreeNode(3).apply {
        left = TreeNode(1).apply {
            right = TreeNode(2)
        }
        right = TreeNode(4)
    }
    
    val k = 1
    println("第${k}小的元素: ${kthSmallest(root, k)}")  // 应该输出1
}

迭代实现

// 定义二叉树节点类
class TreeNode(var `val`: Int) {
    var left: TreeNode? = null
    var right: TreeNode? = null
}

// 查找第k小元素的函数
fun kthSmallest(root: TreeNode?, k: Int): Int {
    val stack = mutableListOf<TreeNode>()
    var current = root
    var kVar = k
    
    while (current != null || stack.isNotEmpty()) {
        while (current != null) {
            stack.add(current)
            current = current.left
        }
        current = stack.removeAt(stack.size - 1)
        kVar--
        if (kVar == 0) {
            return current.`val`
        }
        current = current.right
    }
    
    throw IllegalArgumentException("Tree does not contain k elements")
}

// 测试示例
fun main() {
    // 创建测试二叉搜索树
    //       3
    //      / \
    //     1   4
    //      \
    //       2
    val root = TreeNode(3).apply {
        left = TreeNode(1).apply {
            right = TreeNode(2)
        }
        right = TreeNode(4)
    }
    
    val k = 1
    println("第${k}小的元素: ${kthSmallest(root, k)}")  // 应该输出1
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/786144.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Spring的AOP基础以及AOP的核心概念

2. AOP基础 学习完spring的事务管理之后&#xff0c;接下来我们进入到AOP的学习。 AOP也是spring框架的第二大核心&#xff0c;我们先来学习AOP的基础。 在AOP基础这个阶段&#xff0c;我们首先介绍一下什么是AOP&#xff0c;再通过一个快速入门程序&#xff0c;让大家快速体…

VOS历史话单的非法呼叫话单解决方案,IPSS模块安装到VOS服务器,可大幅度提高安全性!

由于VOS的普及性&#xff0c;不得不承认VOS确实是非常优秀的软交换&#xff0c;但是很多客户在使用过程中都会遇到各种安全问题&#xff0c;比如话费被盗用了&#xff0c;历史话单一堆的非法呼叫话单&#xff0c;严重的影响到了话务安全&#xff0c;并不是那点话费的事了&#…

基于Java+SpringMvc+Vue技术的药品进销存仓库管理系统设计与实现系统(源码+LW+部署讲解)

博主介绍&#xff1a;硕士研究生&#xff0c;专注于信息化技术领域开发与管理&#xff0c;会使用java、标准c/c等开发语言&#xff0c;以及毕业项目实战✌ 从事基于java BS架构、CS架构、c/c 编程工作近16年&#xff0c;拥有近12年的管理工作经验&#xff0c;拥有较丰富的技术架…

python库(8):re库实现字符串处理

1 re库简介 Python 的re库是一个功能强大的正则表达式模块&#xff0c;它允许用户执行各种复杂的字符串匹配和处理任务。 以下是re库的主要功能&#xff1a; 搜索&#xff1a;re.search() 用于搜索字符串中第一次出现的模式。匹配&#xff1a;re.match() 从字符串的开始位置…

echarts实现3D饼图

先看下最终效果 实现思路 使用echarts-gl的曲面图&#xff08;surface&#xff09;类型 通过parametric绘制曲面参数实现3D效果 代码实现 <template><div id"surfacePie"></div> </template> <script setup>import {onMounted} fro…

烧烤炉发霉怎么处理 烧烤炉发霉的原因分析

仓库储存的烧烤炉表面布满了霉菌是什么原因&#xff1f;烧烤炉发霉不仅影响外观和卖点&#xff0c;若是出口给到客户手上还会导致面临客户的索赔的问题 &#xff0c;经ihaoer防霉人士介绍烧烤炉发霉处理方法如下&#xff1a; 烧烤炉发霉的原因分析 一、储存的环境潮湿&#xff…

【算法篇】KMP算法,一种高效的字符串匹配算法

我们今天了解一个字符串匹配算法-KMP算法&#xff0c;内容难度相对来说较高&#xff0c;建议先收藏再细品&#xff01;&#xff01;&#xff01; KMP算法的基本概念 KMP算法是一种高效的字符串匹配算法&#xff0c;由D.E.Knuth&#xff0c;J.H.Morris和V.R.Pratt提出的&#…

SPI协议——对外部SPI操作(跨页读写)

关于W25Q32JVSSIQ的详细内容在之前的两篇文章中已经详细介绍&#xff0c;本文不做太多赘述&#xff0c;如果对芯片的了解有缺失的话&#xff0c;可以参考&#xff1a; SPI协议——对外部SPI Flash操作-CSDN博客 SPI协议——读取外部SPI Flash ID_spi flash 读取id-CSDN博客 目录…

快手矩阵管理系统:引领短视频运营新潮流

在短视频行业蓬勃发展的今天&#xff0c;如何高效运营和优化内容创作已成为企业和创作者关注的焦点。快手矩阵管理系统以其强大的核心功能&#xff0c;为短视频内容的创作、发布和管理提供了一站式解决方案。 智能创作&#xff1a;AI自动生成文案 快手矩阵管理系统的智能创作…

如何快速将Excel定义的表结构转换为MySQL的建表语句

目录 引言 方法一&#xff1a;使用Python编程 步骤一&#xff1a;安装必要的库 步骤二&#xff1a;读取Excel文件 步骤三&#xff1a;编写函数生成建表语句 注意事项 方法二&#xff1a;使用Excel VBA 步骤一&#xff1a;启用VBA编辑器 步骤二&#xff1a;编写VBA代码…

随手记录: Ubuntu NVIDIA显卡驱动安装后 屏幕亮度无法调节 无法连接外显示器等问题

背景 一句话&#xff1a;简单记录帮身边人装系统发现 GPU和外接显示器的无法连接&#xff0c;同时亮度无法调节等新问题 设备型号&#xff1a; 联想笔记本&#xff1a;ThinkBook 16p Gen2CPU&#xff1a;AMD Ryzen 7 5800HGPU&#xff1a;RTX 3060 问题描述及流程&#xff…

金蝶API取数+JSON解析,FDL助力高效数据处理

目录 一、企业介绍 二、业务难题与挑战 商管预算管理瓶颈凸显&#xff1a;金蝶数据手工导出&#xff0c;跨库关联分析时效受限 金蝶API数据提取&#xff1a;挑战重重的技术攻坚战 三、解决方案 商管预算管理升级&#xff1a;API取数JSON解析&#xff0c;FineDataLink助力高效数…

文华财经多空波段均线交易黄金分割线指标公式源码

文华财经多空波段均线交易黄金分割线指标公式源码&#xff1a; 多:EMA(C,3),COLORYELLOW; 空:EMA(C,5),COLOR00FF00; 均衡:EMA(空,5),COLORWHITE; VARF1:COUNT(CROSS(多,均衡),2)1; VARF2:COUNT(CROSS(空,均衡),2)1; ZAI:FILTER(VARF1 AND VARF2,2); DRAWTEXT(ZAI,均衡*…

Java基础回顾

1.一个Java程序有且仅有一个main方法作为程序的入口 由main方法所关联的 2.权限修饰符 修饰类 修饰方法 修饰域 public 都可以访问 都可以访问 都可以访问 protected 不能修饰类 子类可以继承&#xff0c;可以访问&#xff0c;同包下的类也可以访问。可以直接访问父…

JNPF-V5.x重磅来袭!

背景概述 行业背景 低代码⾏业经过⼏年的发展、沉淀&#xff0c;其产品的能⼒定位已逐渐清晰&#xff0c;低代码的核⼼价值是提升专业开发 ⼈员的效率&#xff0c;更便捷的调⽤多种能⼒的接⼝&#xff0c;适合IT能⼒强、IT背景复杂的企业使⽤。同时在客户认知层 ⾯上也以⽇…

【Sql Server】sql server 2019设置远程访问,外网服务器需要设置好安全组入方向规则

大家好&#xff0c;我是全栈小5&#xff0c;欢迎来到《小5讲堂》。 这是《Sql Server》系列文章&#xff0c;每篇文章将以博主理解的角度展开讲解。 温馨提示&#xff1a;博主能力有限&#xff0c;理解水平有限&#xff0c;若有不对之处望指正&#xff01; 目录 前言1、无法链接…

股票分析系统设计方案大纲与细节

股票分析系统设计方案大纲与细节 一、引言 随着互联网和金融行业的迅猛发展,股票市场已成为重要的投资渠道。投资者在追求财富增值的过程中,对股票市场的分析和预测需求日益增加。因此,设计并实现一套高效、精准的股票分析系统显得尤为重要。本设计方案旨在提出一个基于大…

Redis基础教程(十五):Redis GEO地理信息查询与管理

&#x1f49d;&#x1f49d;&#x1f49d;首先&#xff0c;欢迎各位来到我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里不仅可以有所收获&#xff0c;同时也能感受到一份轻松欢乐的氛围&#xff0c;祝你生活愉快&#xff01; &#x1f49d;&#x1f49…

Leetcode—97. 交错字符串【中等】

2024每日刷题&#xff08;140&#xff09; Leetcode—97. 交错字符串 2d动规实现代码 class Solution { public:bool isInterleave(string s1, string s2, string s3) {int m s1.length();int n s2.length();int len s3.length();if(m n ! len) {return false;}vector<…

从零开始做题:easycap

题目 给出一个pcap文件 解题 注&#xff1a;传输控制协议&#xff08;TCP&#xff0c;Transmission Control Protocol&#xff09;是为了在不可靠的互联网络上提供可靠的端到端字节流而专门设计的一个传输协议 .pcap文件需要用Wireshark打开 用Wireshark打开easycap.pcap文…