C++二叉树前中后序遍历(递归&非递归)统一代码格式
统一下二叉树的代码格式,递归和非递归都统一格式,方便记忆管理。
三种递归格式:
前序遍历:
void PreOrder(TreeNode* root, vector<int>&path)
{
if (root)
{
path.emplace_back(root->val);
PreOrder(root->left, path);
PreOrder(root->right, path);
}
}
中序遍历:
void InOrder(TreeNode* root, vector<int>& path)
{
if (root)
{
InOrder(root->left, path);
path.emplace_back(root->val);
InOrder(root->right, path);
}
}
后序遍历:
void PostOrder(TreeNode* root, vector<int>& path)
{
if (root)
{
PostOrder(root->left, path);
PostOrder(root->right, path);
path.emplace_back(root->val);
}
}
三种递归遍历不用多解释。
三种非递归格式:
前序遍历:
void PreOrderCycle(TreeNode* root, vector<int>& path)
{
stack<pair<TreeNode*, bool>> s;
s.emplace(make_pair(root, false));
bool visited;
while (!s.empty())
{
root = s.top().first;
visited = s.top().second;
s.pop();
if (root == NULL)
continue;
if (visited)
path.emplace_back(root->val);
else
{
s.emplace(make_pair(root->right, false));
s.emplace(make_pair(root->left, false));
s.emplace(make_pair(root, true));
}
}
}
中序遍历:
void InOrderCycle(TreeNode* root, vector<int>& path)
{
stack<pair<TreeNode*, bool>> s;
s.emplace(make_pair(root, false));
bool visited;
while (!s.empty())
{
root = s.top().first;
visited = s.top().second;
s.pop();
if (root == NULL)
continue;
if (visited)
path.emplace_back(root->val);
else
{
s.emplace(make_pair(root->right, false));
s.emplace(make_pair(root, true));
s.emplace(make_pair(root->left, false));
}
}
}
后序遍历:
void PostOrderCycle(TreeNode* root, vector<int>& path)
{
stack<pair<TreeNode*, bool>> s;
s.emplace(make_pair(root, false));
bool visited;
while (!s.empty())
{
root = s.top().first;
visited = s.top().second;
s.pop();
if (root == NULL)
continue;
if (visited)
path.emplace_back(root->val);
else
{
s.emplace(make_pair(root, true));
s.emplace(make_pair(root->right, false));
s.emplace(make_pair(root->left, false));
}
}
}
以上三种遍历实现代码行数一模一样,如同递归遍历一样,只有三行核心代码的先后顺序有区别。
解释下三种非递归遍历(以下图举例):

对二叉树而言,将每个框内结点集都看做一个局部,那么局部有 A,A B C,B D E,D,E,C F G,F,G 并且可以发现每个结点元素都是相邻的两个局部的重合结点。
算法流程:
1 每个结点元素都是相邻的两个局部的重合结点。对一个局部排好序后,通过取出一个重合结点过渡到与之相邻的局部进行新的局部排序。
2 用栈来保证局部顺序(排在前面的后入栈,排在后面的先入栈,保证局部元素出栈的顺序一定正确)
3 通过栈顶元素过渡到新局部的排序,对新局部的排序会导致该结点再次入栈,
4 当栈顶出现已完成过渡使命的结点时,就可以彻底出栈输出了,新栈顶元素会继续完成新局部的过渡
5 当所有结点都完成了过渡使命了,就全部出栈了。
参考:
https://www.jianshu.com/p/49c8cfd07410
C++二叉树前中后序遍历(递归&非递归)统一代码格式的更多相关文章
- [C++] 非递归实现前中后序遍历二叉树
目录 前置技能 需求描述 binarytree.h 具体实现 binarytree.cpp main.cpp 网上代码一搜一大片,大同小异咯. 书上的函数实现代码甚至更胜一筹,而且抄一遍就能用,唯一问 ...
- 二叉树前中后/层次遍历的递归与非递归形式(c++)
/* 二叉树前中后/层次遍历的递归与非递归形式 */ //*************** void preOrder1(BinaryTreeNode* pRoot) { if(pRoot==NULL) ...
- Binary Tree Traversal 二叉树的前中后序遍历
[抄题]:二叉树前序遍历 [思维问题]: 不会递归.三要素:下定义.拆分问题(eg root-root.left).终止条件 [一句话思路]: 节点非空时往左移,否则新取一个点 再往右移. [输入量] ...
- POJ 2255 Tree Recovery && Ulm Local 1997 Tree Recovery (二叉树的前中后序遍历)
链接:poj.org/problem?id=2255 本文链接:http://www.cnblogs.com/Ash-ly/p/5463375.html 题意: 分别给你一个二叉树的前序遍历序列和中序 ...
- 数据结构-C语言递归实现树的前中后序遍历
#include <stdio.h> #include <stdlib.h> typedef struct tree { int number ; struct tree *l ...
- C++实现对树的创建和前中后序遍历
#include<iostream>#include<stdio.h> using namespace std; class BitNode{ public: char dat ...
- LeetCode 145 二叉树的后序遍历(非递归)
题目: 给定一个二叉树,返回它的 后序 遍历. 示例: 输入: [1,null,2,3] 1 \ 2 / 3 输出: [3,2,1] 进阶: 递归算法很简单,你可以通过迭代算法完成吗? 解题思路: 1 ...
- 飘逸的python - 极简的二叉树前中后序通杀函数
对于任一结点.能够按某种次序运行三个操作: 訪问结点本身(N) 遍历该结点的左子树(L) 遍历该结点的右子树(R) 用来表示顺序,即,前序NLR/中序LNR/后序LRN. 以下我们用namedtupl ...
- 前中后序递归遍历树的体会 with Python
前序:跟->左->右 中序:左->根->右 后序:左>右->根 采用递归遍历时,编译器/解释器负责将递归函数调用过程压入栈并保护现场,在不同位置处理根节点即可实现不 ...
随机推荐
- eNSP路由器输出 '#' 无法启动的一种解决方法
试过网上的改virtulboxIP.关防火墙.改兼容性等方法,都不成功.后来发现通过改变选择路由器的型号可以启动. 如果对路由器没有特殊需求,可以选择型号数字较小的试一下(最低可以选择Router).
- ParallelForTransform作业
ParallelForTransform作业是另一种ParallelFor作业 ; 专为在变形上操作而设计. 注意:ParallelForTransform作业是Unity中用于实现IJobParal ...
- Leetcode刷题6—不同路径
一.要求 二.知识点 这道题属于动态规划,主要思路就是将大问题不断分解成小问题进行求解 三.解题思路 1.利用数学思路找规律 将m和n组合成一个m*n的矩阵,而且是一个对称阵 [[0],[1],[1] ...
- 输入一个数值num,对1到num的所有的数值进行全排列
输入一个数值num,对1到num的所有的数值进行全排列: 其实这个题目可以看成是将1到num个数字放入num个有序的盒子里面:当将最后一个数字放入盒子里的时候,就输出所有盒子里的数字:这就是一个排列的 ...
- Go语言中的打包和工具链
包 所有Go语言的程序都会组织成若干组文件,每组文件被称为一个包.这样每个包的代码都可以作为很小的复用单元,被其他项目引用. 包名惯例 给包命名的惯例是使用包所在目录的名字.并不需要所有包的名字都与别 ...
- teach-es6-1
------------------------------------------------------------------------字符串连接: 之前: var str=''; var s ...
- ioremap&buddy system
生死契阔,与子成说,执子之手,与子携老 一.ioremap 1.参考: 理解 (1)http://www.linuxidc.com/Linux/2011-04/34295.htm 代码过程 (1)ht ...
- XSS练习平台- https://alf.nu/alert1
https://alf.nu/alert1 参考:https://www.cnblogs.com/renzongxian/p/5617551.html 我目前的进度:https://alf.n ...
- Redis基础与持久化
Redis介绍 软件说明 Redis是一款开源的,ANSI C语言编写的,高级键值(key-value)缓存和支持永久存储NoSQL数据库产品. Redis采用内存(In-Memory)数据集(Dat ...
- 批量导出docker images 的一个简单方法
docker images |cut -c - |xargs docker save -o iamges.tar 主要 最大的长度不能超过 18 超过了就得改一下 -c 后面的数据长度 最终效果为: ...