面试经典算法系列之二叉树5 -- 二叉树的前序遍历

面试经典算法20 - 二叉树的前序遍历

LeetCode.144
公众号:阿Q技术站

问题描述

给你二叉树的根节点 root ,返回它节点值的 前序 遍历。

示例 1:

img

输入:root = [1,null,2,3]
输出:[1,2,3]

示例 2:

输入:root = []
输出:[]

示例 3:

输入:root = [1]
输出:[1]

示例 4:

img

输入:root = [1,2]
输出:[1,2]

示例 5:

img

输入:root = [1,null,2]
输出:[1,2]

提示:

  • 树中节点数目在范围 [0, 100]
  • -100 <= Node.val <= 100

思路

递归
  1. 使用递归进行前序遍历,即根节点 -> 左子树 -> 右子树。
  2. 对于每个节点,先将节点的值加入结果数组,然后递归遍历左子树和右子树。
迭代

遍历,先将根节点压入栈中。然后循环执行以下操作:

  • 弹出栈顶节点,如果节点为空,则继续弹出,直到遇到非空节点。
  • 对于非空节点,先将其值加入结果数组,然后将右子节点压入栈中,再将左子节点压入栈中,保证左子节点在右子节点之前被访问。

图解

这里给大家图解一下迭代的方法。

  1. 先将根节点压入栈中。

image-20240228231435835

  1. 当栈不为空时,弹出栈顶元素,遍历右子节点,再遍历左子节点。

image-20240228234208113

  1. 依次弹出栈顶元素,并添加到结果集。

image-20240228234530533

参考代码

C++
递归
#include <iostream>
#include <vector>
#include <stack>
#include <unordered_map>using namespace std;// 定义二叉树节点
struct TreeNode {int val;TreeNode* left;TreeNode* right;TreeNode(int x) : val(x), left(NULL), right(NULL) {}
};class Solution {
public:vector<int> preorderTraversal(TreeNode* root) {vector<int> result;preorder(root, result);return result;}void preorder(TreeNode* root, vector<int>& result) {if (root == nullptr) {return;}result.push_back(root->val); // 将当前节点的值加入结果数组preorder(root->left, result); // 递归遍历左子树preorder(root->right, result); // 递归遍历右子树}
};// 创建二叉树
TreeNode* createTree() {TreeNode* root = new TreeNode(1);root->right = new TreeNode(2);root->right->left = new TreeNode(3);return root;
}// 打印结果
void printResult(const vector<int>& result) {cout << "前序遍历结果:";for (int val : result) {cout << val << " ";}cout << endl;
}int main() {Solution sol;TreeNode* root = createTree();vector<int> result = sol.preorderTraversal(root);printResult(result);return 0;
}
迭代
#include <iostream>
#include <vector>
#include <stack>using namespace std;// 二叉树节点的定义
struct TreeNode {int val;TreeNode* left;TreeNode* right;TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
};// 非递归前序遍历
vector<int> preorderTraversal(TreeNode* root) {vector<int> result; // 存储遍历结果的数组if (!root) return result; // 如果根节点为空,直接返回空数组stack<TreeNode*> st; // 辅助栈,用于存储遍历过程中的节点st.push(root); // 将根节点入栈while (!st.empty()) { // 当栈非空时循环执行以下操作TreeNode* node = st.top(); // 获取栈顶节点st.pop(); // 弹出栈顶节点result.push_back(node->val); // 将节点值加入结果数组if (node->right) { // 如果节点有右子节点,将右子节点入栈st.push(node->right);}if (node->left) { // 如果节点有左子节点,将左子节点入栈st.push(node->left);}}return result; // 返回结果数组
}// 创建二叉树
TreeNode* createTree(vector<int>& nodes, int index) {if (index >= nodes.size() || nodes[index] == -1) {return nullptr; // 如果节点为空,则返回nullptr}TreeNode* root = new TreeNode(nodes[index]); // 创建当前节点root->left = createTree(nodes, 2 * index + 1); // 创建左子树root->right = createTree(nodes, 2 * index + 2); // 创建右子树return root; // 返回当前节点
}// 销毁二叉树
void destroyTree(TreeNode* root) {if (!root) return; // 如果根节点为空,直接返回destroyTree(root->left); // 递归销毁左子树destroyTree(root->right); // 递归销毁右子树delete root; // 删除当前节点
}int main() {vector<int> nodes = {1, 2, 3, -1, -1, 4, 5}; // 定义二叉树的先序遍历序列TreeNode* root = createTree(nodes, 0); // 创建二叉树vector<int> result = preorderTraversal(root); // 进行非递归前序遍历for (int val : result) { // 输出遍历结果cout << val << " ";}cout << endl;destroyTree(root); // 销毁二叉树return 0;
}
Java
import java.util.*;// 二叉树节点的定义
class TreeNode {int val;TreeNode left;TreeNode right;TreeNode(int x) { val = x; }
}public class Main {// 非递归前序遍历public List<Integer> preorderTraversal(TreeNode root) {List<Integer> result = new ArrayList<>(); // 存储遍历结果的数组if (root == null) return result; // 如果根节点为空,直接返回空数组Stack<TreeNode> stack = new Stack<>(); // 辅助栈,用于存储遍历过程中的节点stack.push(root); // 将根节点入栈while (!stack.isEmpty()) { // 当栈非空时循环执行以下操作TreeNode node = stack.pop(); // 获取栈顶节点result.add(node.val); // 将节点值加入结果数组if (node.right != null) { // 如果节点有右子节点,将右子节点入栈stack.push(node.right);}if (node.left != null) { // 如果节点有左子节点,将左子节点入栈stack.push(node.left);}}return result; // 返回结果数组}// 创建二叉树public TreeNode createTree(int[] nodes, int index) {if (index >= nodes.length || nodes[index] == -1) {return null; // 如果节点为空,则返回null}TreeNode root = new TreeNode(nodes[index]); // 创建当前节点root.left = createTree(nodes, 2 * index + 1); // 创建左子树root.right = createTree(nodes, 2 * index + 2); // 创建右子树return root; // 返回当前节点}// 销毁二叉树public void destroyTree(TreeNode root) {if (root == null) return; // 如果根节点为空,直接返回destroyTree(root.left); // 递归销毁左子树destroyTree(root.right); // 递归销毁右子树}public static void main(String[] args) {Main solution = new Main();int[] nodes = {1, 2, 3, -1, -1, 4, 5}; // 定义二叉树的先序遍历序列TreeNode root = solution.createTree(nodes, 0); // 创建二叉树List<Integer> result = solution.preorderTraversal(root); // 进行非递归前序遍历for (int val : result) { // 输出遍历结果System.out.print(val + " ");}System.out.println();solution.destroyTree(root); // 销毁二叉树}
}
Python
# 二叉树节点的定义
class TreeNode:def __init__(self, x):self.val = xself.left = Noneself.right = None# 非递归前序遍历
def preorderTraversal(root):result = [] # 存储遍历结果的数组if not root:return result # 如果根节点为空,直接返回空数组stack = [] # 辅助栈,用于存储遍历过程中的节点stack.append(root) # 将根节点入栈while stack: # 当栈非空时循环执行以下操作node = stack.pop() # 获取栈顶节点result.append(node.val) # 将节点值加入结果数组if node.right: # 如果节点有右子节点,将右子节点入栈stack.append(node.right)if node.left: # 如果节点有左子节点,将左子节点入栈stack.append(node.left)return result # 返回结果数组# 创建二叉树
def createTree(nodes, index):if index >= len(nodes) or nodes[index] == -1:return None # 如果节点为空,则返回Noneroot = TreeNode(nodes[index]) # 创建当前节点root.left = createTree(nodes, 2 * index + 1) # 创建左子树root.right = createTree(nodes, 2 * index + 2) # 创建右子树return root # 返回当前节点# 销毁二叉树
def destroyTree(root):if not root:return # 如果根节点为空,直接返回destroyTree(root.left) # 递归销毁左子树destroyTree(root.right) # 递归销毁右子树# 主函数
if __name__ == "__main__":nodes = [1, 2, 3, -1, -1, 4, 5] # 定义二叉树的先序遍历序列root = createTree(nodes, 0) # 创建二叉树result = preorderTraversal(root) # 进行非递归前序遍历print(result) # 输出遍历结果destroyTree(root) # 销毁二叉树

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

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

结合ArcGIS+SWAT模型+Century模型:流域生态系统水-碳-氮耦合过程模拟

原文链接&#xff1a;结合ArcGISSWAT模型Century模型&#xff1a;流域生态系统水-碳-氮耦合过程模拟https://mp.weixin.qq.com/s?__bizMzUzNTczMDMxMg&tempkeyMTI2NV9sMGRZNUJoVkNVc1ZzSzRuMl9XXzhqX0R3cXpESWFwM1E4cFY4ejNqWFh3VUl0dlZkNWk4b20ydFdFTy1xS2ZObGN0Z0ZXSjly…

怎么在外地控制自家的电视

怎么在外地控制自家的电视 随着科技的进步和智能家居的普及&#xff0c;远程控制家中的电器设备已经成为现实。电视作为家庭娱乐的中心&#xff0c;远程控制功能更是备受关注。那么&#xff0c;如何在外地控制自家的电视呢&#xff1f;本文将为你提供详细的步骤和有价值的信息…

医院订餐平台:为患者提供贴心服务的创新解决方案

在现代医疗服务中&#xff0c;患者的就餐问题一直是一个备受关注的议题。传统的医院饮食服务往往面临着餐品单一、服务不及时等问题&#xff0c;无法满足患者的个性化需求。为了提高患者的就餐体验&#xff0c;医院订餐平台应运而生&#xff0c;通过数字化、个性化的服务&#…

【域适应】基于深度域适应MMD损失的典型四分类任务实现

关于 MMD &#xff08;maximum mean discrepancy&#xff09;是用来衡量两组数据分布之间相似度的度量。一般地&#xff0c;如果两组数据分布相似&#xff0c;那么MMD 损失就相对较小&#xff0c;说明两组数据/特征处于相似的特征空间中。基于这个想法&#xff0c;对于源域和目…

【HTML】制作一个简单的线性动画

目录 前言 HTML部分 CSS部分 JS部分 效果图 总结 前言 无需多言&#xff0c;本文将详细介绍一段HTML代码&#xff0c;具体内容如下&#xff1a; 开始 首先新建文件夹&#xff0c;创建一个文本文档&#xff0c;两个文件夹&#xff0c;其中HTML的文件名改为[index.html]&am…

前端对接fastGPT流式数据+打字机效果

首先在对接api时 参数要设置stream: true, const data {chatId: abc,stream: true,//这里true返回流式数据detail: false,variables: {uid: sfdsdf,name: zhaoyunyao,},messages: [{ content: text, role: user }]}; 不要用axios发请求 不然处理不了流式数据 我这里使用fetch …

赋能技术 助锂制造|青软青之助力锂电检测行业数字化升级

在全球范围内&#xff0c;新能源转型已成为时代的必然选择。随着“双碳”目标的深入推进&#xff0c;这一趋势愈发明显。而作为新能源领域的一颗璀璨明珠&#xff0c;锂电池的研发、产业链建设和技术创新&#xff0c;无疑是这场能源革命的核心所在。其产业链的日趋完善、技术的…

通过WebShell登录SQL Server主机并使用SSRS报表服务

背景信息 RDS SQL Server提供了WebShell功能&#xff0c;允许用户通过Web界面登录到RDS SQL Server实例的操作系统中&#xff0c;并在该操作系统中执行命令、上传下载文件等操作。WebShell功能方便用户对RDS SQL Server实例的管理和维护&#xff0c;特别是在无法使用SSH客户端的…

PyTorch-Lightning:trining_step的自动优化

文章目录 PyTorch-Lightning&#xff1a;trining_step的自动优化总结&#xff1a; class _ AutomaticOptimization()def rundef _make_closuredef _training_stepclass ClosureResult():def from_training_step_output class Closure PyTorch-Lightning&#xff1a;trining_ste…

纯小白蓝桥杯备赛笔记--DAY14(计算几何)

文章目录 计算几何基础平面几何距离圆的周长和面积圆与圆之间的关系&#xff1a;海伦公式计算三角形面积点到直线的距离 点积和叉积例题&#xff1a; 点和线的关系点的表示形式和代码判断点在直线的那边点到线的垂足点到线的距离例题-1242例题-1240升级--点到线段的距离--1285 …

基于级联H桥的多电平逆变器PWM控制策略的simulink建模与仿真

目录 1.课题概述 2.系统仿真结果 3.核心程序与模型 4.系统原理简介 5.完整工程文件 1.课题概述 级联H桥&#xff08;CHB&#xff09;多电平逆变器是一种通过多个H桥单元级联实现更高电压等级和更高质量输出波形的电力电子转换装置。这种逆变器在高压大功率场合应用广泛&am…

软考123-上午题-【软件工程】-系统设计

一、系统设计 1-1、概要设计 设计软件系统总结结构数据结构及数据库设计编写概要设计文档评审 1-1-1、设计软件系统总结结构 其基本任务是采用某种设计方法&#xff0c;将一个复杂的系统按功能划分成模块&#xff1b; 确定每个模块的功能&#xff1b;确定模块之间的调用关系…