三、二叉树-算法总结

文章目录

  • 三、二叉树
    • 3.1 二叉树遍历
      • 3.1.1 前序遍历
      • 3.1.2 中序遍历
      • 3.1.3 后序遍历
      • 3.1.4 DFS 深度搜索
      • 3.1.5 BFS 广度搜索
      • 3.1.6 BFS 广度搜索 2
    • 3.2 二叉树分治
      • 3.2.1 检验二叉搜索树
      • 3.2.2 二叉树的最大深度
      • 3.2.3 平衡二叉树
    • 3.3 二叉树分治法
      • 3.3.1 二叉树中的最大路径和
      • 3.3.2 二叉树的最近的公共祖先

三、二叉树

3.1 二叉树遍历

3.1.1 前序遍历

144. 二叉树的前序遍历
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*//**method1: 基于递归的先序遍历*/
// class Solution {
//     private List<Integer> nums = new ArrayList<>();
//     public List<Integer> preorderTraversal(TreeNode root) {
//         preIter(root);
//         return nums;
//     }//     private void preIter(TreeNode node){
//         if(node == null){
//             return;
//         }
//         nums.add(node.val);
//         preIter(node.left);
//         preIter(node.right);
//     }// }/**
method2: 基于stack的非递归先序遍历*/
class Solution {public List<Integer> preorderTraversal(TreeNode root) {List<Integer> list = new ArrayList<>();Stack<TreeNode> stack = new Stack<>();TreeNode p = root;while(p != null || !stack.isEmpty()){// 依次定位左边的子树,直至最左侧的子节点while(p!=null){list.add(p.val);stack.push(p);p = p.left;}// 出栈定位结点的右子树if(!stack.isEmpty()){p = stack.pop();p = p.right;}}return list;}
}

3.1.2 中序遍历

94. 二叉树的中序遍历
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*//**method1: 基于递归的中序遍历*/
// class Solution {
//     private List<Integer> nums = new ArrayList<>();
//     public List<Integer> inorderTraversal(TreeNode root) {
//         midIter(root);
//         return nums;
//     }//     private void midIter(TreeNode node){
//         if(node == null){
//             return;
//         }
//         preIter(node.left);
//         nums.add(node.val);
//         preIter(node.right);
//     }// }/**
method2:基于stack的非递归中序遍历*/
class Solution {public List<Integer> inorderTraversal(TreeNode root) {List<Integer> list = new ArrayList<>();Stack<TreeNode> stack = new Stack<>();TreeNode p = root;while(p != null || !stack.isEmpty()){while(p != null){stack.push(p);p = p.left;}if(!stack.isEmpty()){p = stack.pop();list.add(p.val);p = p.right;}}return list;}}

3.1.3 后序遍历

145. 二叉树的后序遍历
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*//**method1: 基于递归的后序遍历*/
// class Solution {
//     private List<Integer> nums = new ArrayList<>();//     public List<Integer> postorderTraversal(TreeNode root) {
//         postOrder(root);
//         return nums;
//     }//     private void postOrder(TreeNode node){
//         if(node == null){
//             return;
//         }
//         postOrder(node.left);
//         postOrder(node.right);
//         nums.add(node.val);
//     }
// }/**method2: 基于stack的非递归后序遍历*/
class Solution {public List<Integer> postorderTraversal(TreeNode root) {List<Integer> result = new ArrayList<>();Stack<TreeNode> stack = new Stack<TreeNode>();TreeNode p = root;// 通过lastVisit标识右子节点是否已经弹出TreeNode lastVisit = root;while (p != null || !stack.isEmpty()) {while (p != null) {stack.push(p);p = p.left;}//查看当前栈顶元素p = stack.peek();//如果其右子树也为空,或者右子树已经访问,则可以访问if (p.right == null || p.right == lastVisit) {result.add(p.val);stack.pop();// 标记当前这个节点已经弹出过lastVisit = p;p = null;} else {//否则继续遍历右子树p = p.right;}}return result;
}}

3.1.4 DFS 深度搜索

257. 二叉树的所有路径
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*/
class Solution {public List<String> binaryTreePaths(TreeNode root) {List<String> paths = new ArrayList<>();dfs(root, new StringBuffer(), paths);return paths;}private void dfs(TreeNode node,StringBuffer path,List<String> paths){if(node == null){return;}path.append(node.val);// 当前结点是叶子结点时,将路径信息加入集合if(node.left == null && node.right == null){paths.add(path.toString());return;}path.append("->");// 当前是非叶子结点dfs(node.left,new StringBuffer(path),paths);dfs(node.right,new StringBuffer(path),paths);}
}

3.1.5 BFS 广度搜索

102. 二叉树的层序遍历
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*/
class Solution {// method:借用队列完成层次遍历public List<List<Integer>> levelOrder(TreeNode root) {if (root == null) {return new ArrayList<>();}Queue<TreeNode> queue = new LinkedList<>();queue.add(root);TreeNode node;int n;List<List<Integer>> result = new ArrayList<>();List<Integer> layerOrder;while (!queue.isEmpty()) {// 某一层的结点个数n = queue.size();layerOrder = new ArrayList<>();for(int i = 0 ;i<n;i++){node = queue.poll();layerOrder.add(node.val);if(node.left != null){queue.add(node.left);}if(node.right != null){queue.add(node.right);}}result.add(layerOrder);}return result;}
}

3.1.6 BFS 广度搜索 2

107. 二叉树的层序遍历 II
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*/
class Solution {public List<List<Integer>> levelOrderBottom(TreeNode root) {if(root == null){return new ArrayList<>();}Queue<TreeNode> queue = new LinkedList<>();queue.add(root);TreeNode p;int n;List<List<Integer>> result = new ArrayList<>();List<Integer> layerOrder;while(!queue.isEmpty()){n = queue.size();layerOrder = new ArrayList<>();for(int i = 0;i<n;i++){p = queue.poll();layerOrder.add(p.val);if(p.left != null){queue.add(p.left);}if(p.right != null){queue.add(p.right);}}result.add(layerOrder);}Collections.reverse(result); // 反转return result;}
}

3.2 二叉树分治

先分别处理局部,在合并结果
分支模板

  • 递归返回条件
  • 分段处理
  • 合并结果
public ResultType traversal(TreeNode root) {// null or leafif (root == null) {// do something and return}// DivideResultType left = traversal(root.Left)ResultType right = traversal(root.Right)// ConquerResultType result = Merge from left and rightreturn result
}

3.2.1 检验二叉搜索树

98. 验证二叉搜索树
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*/
class Solution {// method1: 基于中序遍历查找是否逆序// 时间复杂度 O(n)// 空间复杂度 O(n)// public boolean isValidBST(TreeNode root) {//     List<Integer> list = new ArrayList<>();//     midOrder(root,list);//     for(int i = 0;i<list.size()-1;i++){//         if(list.get(i) >= list.get(i+1)){//             return false;//         }//     }//     return true;// }// private void midOrder(TreeNode node,List<Integer> list){//     if(node == null){   //         return;//     }//     midOrder(node.left,list);//     list.add(node.val);//     midOrder(node.right,list);// }// method: 基于自顶向下遍历的判断方法// 时间复杂度:O(n)// 空间复杂度:O(H) 树的高度 public boolean isValidBST(TreeNode root) {return isValid(root,Long.MIN_VALUE,Long.MAX_VALUE);}private boolean isValid(TreeNode node,long min,long max){if(node == null){return true;}// 以当前结点作为子节点,比对它与其父节点的大小关系if(node.val <= min || node.val >= max){return false;}boolean left = isValid(node.left,min,node.val);boolean right = isValid(node.right,node.val,max);return left&&right;}}

3.2.2 二叉树的最大深度

104. 二叉树的最大深度
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*/
class Solution {public int maxDepth(TreeNode root) {return height(root);}private int height(TreeNode node){if(node == null){return 0;}return Math.max(height(node.left),height(node.right)) + 1;}
}

3.2.3 平衡二叉树

110. 平衡二叉树
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*/
class Solution {public boolean isBalanced(TreeNode root) {return maxDepth(root) >= 0;
}private int maxDepth(TreeNode p) {if (p == null) {return 0;}int left = maxDepth(p.left);int right = maxDepth(p.right);// 小于0代表存在非平衡子树(则依次向上传导)if (left < 0 || right < 0 || Math.abs(left - right) > 1) {return -1;} else {return Math.max(left, right) + 1;}
}
}

3.3 二叉树分治法

3.3.1 二叉树中的最大路径和

124. 二叉树中的最大路径和
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode() {}*     TreeNode(int val) { this.val = val; }*     TreeNode(int val, TreeNode left, TreeNode right) {*         this.val = val;*         this.left = left;*         this.right = right;*     }* }*/
class Solution {public int maxPathSum(TreeNode root) {return maxPathDFS(root)[1];}// int[0]:表示子树(经过子树的根节点)的单边收益(设置下限为0)// int[1]:表示子树(经过子树的根节点)的内部最大路径和public int[] maxPathDFS(TreeNode node){// 叶子结点的"虚拟"子树返回if(node == null){return new int[]{0,Integer.MIN_VALUE};}// Divideint[] left = maxPathDFS(node.left);int[] right = maxPathDFS(node.right);int singleSum,bothSum;// Conquer// 获取经过当前树根节点的单边最大收益if(left[0] > right[0]){singleSum = Math.max(0,left[0]+node.val);}else{singleSum = Math.max(0,right[0]+node.val);}// 比较当前子树的内部路径和与其子树的内部路径bothSum = Math.max(left[1],right[1]);bothSum = Math.max(bothSum,left[0] + right[0] + node.val);return new int[]{singleSum,bothSum};}
}

3.3.2 二叉树的最近的公共祖先

236. 二叉树的最近公共祖先
在这里插入图片描述

/*** Definition for a binary tree node.* public class TreeNode {*     int val;*     TreeNode left;*     TreeNode right;*     TreeNode(int x) { val = x; }* }*/
class Solution {public TreeNode lowestCommonAncestor(TreeNode root, TreeNode p, TreeNode q) {return lowestCom(root,p,q);}private TreeNode lowestCom(TreeNode node, TreeNode p, TreeNode q){if(node == null || node == p || node == q){return node;}TreeNode left = lowestCom(node.left, p, q);TreeNode right = lowestCom(node.right, p, q);if(left != null && right != null){return node;}return left != null ? left:right;}
}

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

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

mysql数据库如何开启binlog日志

首先我们要知道什么是binlog日志 binlog是 MySQL数据库的二进制日志文件&#xff0c;记录了数据库更改的所有操作&#xff0c;但不包括SELECT和SHOW这类操作&#xff0c;这些操作对数据进行修改、管理操作、数据库修改等操作都会被记录在日志中。 对于一个sql&#xff0c;它…

Qt-QPushButton按钮类控件(22)

目录 描述 使用 给按钮添加图片 给按钮添加快捷键 添加槽函数 添加快捷键 添加组合键 开启鼠标的连发功能 描述 经过上面的一些介绍&#xff0c;我们也尝试的使用过了这个控件&#xff0c;接下来我们就要详细介绍这些比较重要的控件了 使用 给按钮添加图片 我们创建…

在线IP代理检测:保护您的网络安全

在互联网飞速发展的今天&#xff0c;越来越多的人开始意识到网络安全和隐私保护的重要性。在线IP代理检测工具作为一种有效的网络安全手段&#xff0c;能够帮助用户识别和检测IP代理的使用情况&#xff0c;从而更好地保护个人隐私和数据安全。本文将详细介绍在线IP代理检测的相…

最好用的翻译器:什么是DeepL?如何订阅支付DeepL,订阅DeepL Pro以及申请DeepL API?

DeepL目前最好用的翻译软件&#xff0c;如果是学习翻译的同学或者海外客户翻译&#xff0c;一定不能错过&#xff0c;用它来处理文件&#xff0c;论文等翻译是最好不过了的&#xff01;&#xff01;&#xff01; AI翻译技术的飞速发展正在颠覆我们的沟通方式&#xff0c;打破语…

预测日前电价:回顾最先进的算法、最佳实践和公开基准——阅读笔记

Forecasting day-ahead electricity prices: A review of state-of-the-art algorithms, best practices and an open-access benchmark 预测日前电价&#xff1a;回顾最先进的算法、最佳实践和公开基准 Applied Energy (2021) 摘要&#xff1a;电价预测在过去二十年间已经得到…

【pycharm】安装以及简单使用教程

以windows版本举例&#xff1a; 1、首先去Pycharm官网&#xff0c;或者直接输入网址&#xff1a;http://www.jetbrains.com/pycharm/download/#sectionwindows&#xff0c;下载PyCharm安装包&#xff0c;根据自己电脑的操作系统进行选择&#xff0c;对于windows系统选择下图的…

苹果CMS影视程序被举报侵权?有效解决方案指南

在当今数字时代&#xff0c;影视版权问题成为了许多网站面临的主要挑战。如果你使用苹果CMS进行影视内容管理&#xff0c;可能会遇到版权举报的问题。幸运的是&#xff0c;有一种有效的解决方案可以帮助你应对这些挑战——苹果CMS插件&#xff0c;它能够屏蔽原视频内容&#xf…

网络药理学:2、文章基本思路、各个数据库汇总与比对、其他相关资料(推荐复现的文章、推荐学习视频、论文基本框架、文献基本知识及知网检索入门)

一、文章基本思路&#xff08;待更&#xff09; 一篇不含分子对接和实验的纯网络药理学文章思路如下&#xff1a; 即如下&#xff1a; 二、 各个数据库&#xff08;待更&#xff09; 三、其他相关资料 1.推荐复现的文章 纯网络药理学分子对接&#xff1a;知网&#xff1…

《C++》解密--顺序表

一、线性表 线性表是n个具有相同特性的数据元素的有限序列。 线性表是一种在实际中广泛使用的数据结构&#xff0c;常见的线性表&#xff1a;顺序表、链表、栈...... 线性表在【逻辑上】是线性结构…

单调队列的实现

这是C算法基础-数据结构专栏的第二十五篇文章&#xff0c;专栏详情请见此处。 引入 单调队列就是满足单调性的队列&#xff0c;它最经典的应用就是给定一个序列和一个窗口&#xff0c;使窗口在序列中从前向后滑动&#xff0c;求出窗口在每个位置时&#xff0c;其中元素的最大/小…

STM32启用FPU浮点运算

这篇文章产生背景&#xff1a;其他人的文章太杂了&#xff0c;对我这种菜鸡无法接受&#xff1b; 参考文章&#xff1a; stm32h743单片机嵌入式学习笔记7-FPU_stmh743vit4-CSDN博客 stm32F407 打开 FPU(浮点运算处理器)_stm32f407开启fpu-CSDN博客 STM32F4CubeMXHal库下使能…

第J1周:ResNet-50算法实战与解析

&#x1f368; 本文为&#x1f517;365天深度学习训练营 中的学习记录博客&#x1f356; 原作者&#xff1a;K同学啊 文章目录 一、前期工作1、ResNet-50总体结构2、设置GPU3、导入数据 二、数据预处理1、加载数据2、可视化数据3、再次检查数据4、配置数据集 三、构建ResNet-50…

初级练习[2]:Hive SQL查询汇总分析

目录 SQL查询汇总分析 成绩查询 查询编号为“02”的课程的总成绩 查询参加考试的学生个数 分组查询 查询各科成绩最高和最低的分 查询每门课程有多少学生参加了考试(有考试成绩) 查询男生、女生人数 分组结果的条件 查询平均成绩大于60分的学生的学号和平均成绩 查询至少…

基于python+django+vue的农业管理系统

作者&#xff1a;计算机学姐 开发技术&#xff1a;SpringBoot、SSM、Vue、MySQL、JSP、ElementUI、Python、小程序等&#xff0c;“文末源码”。 专栏推荐&#xff1a;前后端分离项目源码、SpringBoot项目源码、SSM项目源码 系统展示 【2025最新】基于pythondjangovueMySQL的农…

C++ push_back和emplace_back的区别

基本类型情况西&#xff0c;两者几乎没什么区别 但是再自定义类型的时候&#xff1f;emplace——back更高效&#xff0c;但是emplace_back 没有类型检查的安全&#xff1b;只有运行时候才会报错。 #include <vector> #include <iostream> using namespace std; …

基于 CycleGAN 对抗网络的自定义数据集训练

目录 生成对抗网络&#xff08;GAN&#xff09; CycleGAN模型训练 训练数据生成 下载开源项目CycleGAN 配置训练环境 开始训练 模型测试 可视化结果 生成对抗网络&#xff08;GAN&#xff09; 首先介绍一下什么是GAN网络&#xff0c;它是由生成器&#xff08;Generator…

分类预测|基于差分优化DE-支持向量机数据分类预测完整Matlab程序 DE-SVM

分类预测|基于差分优化DE-支持向量机数据分类预测完整Matlab程序 DE-SVM 文章目录 一、基本原理DE-SVM 分类预测原理和流程总结 二、实验结果三、核心代码四、代码获取五、总结 一、基本原理 DE-SVM 分类预测原理和流程 1. 差分进化优化算法&#xff08;DE&#xff09; 原理…

【运维监控】Prometheus+grafana监控tomcat运行情况

运维监控系列文章入口&#xff1a;【运维监控】系列文章汇总索引 文章目录 一、prometheus二、grafana三、tomcat与jmx_exporter配置1、下载jmx_exporter2、部署jmx_exporter3、添加tomcat的配置信息4、修改tomcat的启动文件5、重启tomcat及验证6、其他 四、集成prometheus与gr…

vue3 动态 svg 图标使用

前言 在做后台管理系统中,我们经常会用到很多图标,比如左侧菜单栏的图标 当然这里 element-ui 或者 element-plus 组件库都会提供图标 但是在有些情况下 element-ui 或者 element-plus 组件库提供的图标满足不了我们的需求时,这个时候我们就需要自己去网上找一些素材或者…

CAN通讯常见错误

CAN通讯常见错误 1.在使用CAN设备进行数据通讯时&#xff0c;有时候参数配置不当可能就会导致通讯的失败&#xff0c;如下图1所示&#xff0c;出现通信错误的原因是两个设备的波特率配置不一致导致。 图1 2.有时候在配置参数的时候&#xff0c;不能只关注波特率速度配置一致…