后序遍历

二叉树的非递归遍历的思想

痴心易碎 提交于 2019-12-20 18:14:28
最近在学习数据结构,从书上的代码示例中学习到了一种抽象的思考方式,记录一些学习二叉树的感悟 先序遍历 先序遍历相对简单,我一开实现的时候考虑了四种情况 左孩子为空 && 右孩子为空 访问根节点,然后出栈 左孩子不为空 && 右孩子为空 访问根节点,然后继续访问左孩子 左孩子为空 && 右孩子不为空 访问根节点,入栈右孩子,出栈 左孩子不为空 && 右孩子不为空 访问根节点,入栈右孩子,继续访问左孩子 template<typename Elemtype> template<typename Fun> bool BiTree<Elemtype>::PreOrderTraverse(Fun &visit){ Stack<BiTNode<Elemtype>*> S; InitStack<bool,BiTNode<Elemtype>*>(S); BiTNode<Elemtype> *p = root; while (p != nullptr) { visit(p); if(p->rChrilde != nullptr) Push<bool,BiTNode<Elemtype>*>(S,p->rChrilde); if(p->lChrilde != nullptr) p = p->lChrilde; else //如果栈空Pop()返回false,用于判断栈空结束循环 if(!Pop<bool

145. 二叉树的后序遍历(C语言)非递归

纵然是瞬间 提交于 2019-12-20 13:58:32
int* postorderTraversal(struct TreeNode* root, int* returnSize){ int *ret=(int*)malloc(sizeof(int)*100); struct TreeNode** stack=(struct TreeNode**)malloc(sizeof(struct TreeNode*)*100); int top=-1; *returnSize=0; if(root) stack[++top]=root; struct TreeNode*cur=NULL,*pre=NULL; while(top!=-1){ cur=stack[top]; //根节点入栈 if((cur->left==NULL&&cur->right==NULL)||(pre&&(pre==cur->left||pre==cur->right))) { //条件1:是叶子节点,则输出 或者条件2:是访问过的叶子节点的爸爸,则输出 //这样保证了从最下方的只有三个元素子树开始输出 ret[(*returnSize)++]=cur->val; top--; pre=cur; } else{//开始这里else丢了,调了好久,逻辑不对 if(cur->right){ stack[++top]=cur->right;//右子节点入栈 } if(cur-

go语言浅析二叉树

自作多情 提交于 2019-12-19 04:47:26
Hello,各位小伙伴大家好,我是小栈君,今天给大家带来的分享是关于关于二叉树相关的知识点,并用go语言实现一个二叉树和对二叉树进行遍历。 我们主要针对二叉树的概念,go实战实现二叉树的前序遍历、中序遍历、后序遍历。 二叉树概念 在计算机科学领域内,二叉树代表的是具有两个节点的树形结构,通常子树被称作为“左子树”,右边的被称作为“右子树”。二叉树通常的应用于实现二叉查找树和二叉堆。 例如上述图片中,我们就制定了一个二叉树,其中d、e、f称作a树的叶子节点。 [叶子结点是离散数学中的概念。一棵树当中没有子结点(即度为0)的结点称为叶子结点,简称“叶子”。 叶子是指出度为0的结点,又称为终端结点] b和c 作为树a的孩子结点,b和a因为作为一个根a的孩子,所以他们的称呼为兄弟结点。其实总结一点就是关于二叉树各个结点的称呼其实和我们在家庭中,对于各个亲戚长辈的称呼类似。 在百度百科中也归纳除了关于二叉树的分类 一棵深度为k,且有2^k-1个结点的二叉树,称为满二叉树。这种树的特点是每一层上的结点数都是最大结点数。而在一棵二叉树中,除最后一层外,若其余层都是满的,并且或者最后一层是满的,或者是在右边缺少连续若干结点,则此二叉树为完全二叉树。 具有n个结点的完全二叉树的深度为floor(log2n) 1。深度为k的完全二叉树,至少有2k-1个叶子结点,至多有2k-1个结点。

非递归遍历二叉树(详解)

扶醉桌前 提交于 2019-12-19 03:19:05
本文转载自: http://blog.csdn.net/zhangxiangdavaid/article/details/37115355 前言   对于二叉树的递归遍历比较简单,所以本文主要讨论的是非递归版。其中,中序遍历的非递归写法最简单,后序遍历最难。    节点的定义: //Binary Tree Node typedef struct node { int data; struct node* lchild; //左孩子 struct node* rchild; //右孩子 }BTNode;   首先,有一点是明确的:非递归写法一定会用到栈,这个应该不用太多的解释。我们先看中序遍历: 中序遍历 分析   中序遍历的递归定义:先左子树,后根节点,再右子树。如何写非递归代码呢?一句话:让代码跟着思维走。我们的思维是什么?思维就是中序遍历的路径。假设,你面前有一棵二叉树,现要求你写出它的中序遍历序列。如果你对中序遍历理解透彻的话,你肯定先找到左子树的最下边的节点。那么下面的代码就是理所当然的: 中序代码段(i) BTNode* p = root; //p指向树根 stack <BTNode*> s; //STL中的栈 //一直遍历到左子树最下边,边遍历边保存根节点到栈中 while (p) { s.push(p); p = p->lchild; }  

数据结构---二叉树遍历

和自甴很熟 提交于 2019-12-18 22:27:55
二叉树遍历可以使用 深度优先遍历 和 广度优先遍历 ,深度优先又可以分为 前序、中序、后序 三种方式遍历,每种方式都可以通过递归和非递归方法实现。 一、深度优先递归遍历: 前序遍历算法: 先遍历根结点 再递归遍历左子树 最后递归遍历右子树 首先访问根结点A; 遍历A结点的左子树,B结点。 B结点有子结点,再按照前序遍历方式遍历,先访问根结点,即B; 遍历B结点左子树,D结点; D结点没有子结点,遍历B结点的右子树,E结点;到此,B结点的根结点、左子树、右子树、已经遍历完成; 遍历A结点的右子树,C结点; C结点有子结点,再按照前序遍历方式遍历,先访问根结点,即C; 遍历C结点左子树,F结点; F结点没有子结点,遍历C结点的右子树,G结点;到此,C结点的根结点、左子树、右子树、已经遍历完成; 最终的访问顺序为:A->B->D->E->C->F->G 代码实现: 结点类: //结点 public class TreeNode { private String data ; private TreeNode left ; private TreeNode right ; public TreeNode ( String data , TreeNode left , TreeNode right ) { this . data = data ; this . left = left ;

二叉树的前序、中序、后序遍历(递归、非递归)实现

寵の児 提交于 2019-12-17 08:37:21
本文部分来源于CSDN 兰亭风雨 大牛的原创。链接为 http://blog.csdn.net/ns_code/article/details/12977901 因为感觉大牛讲的很好,所以这里的文字讲解采用大牛的,大家可以直接看原创!代码部分是我自己的,leetcode代码,可在leetcode Accepted 二叉树是一种非常重要的数据结构,很多其他数据机构都是基于二叉树的基础演变过来的。二叉树有前、中、后三种遍历方式,因为树的本身就是用递归定义的,因此采用递归的方法实现三种遍历,不仅代码简洁且容易理解,但其开销也比较大,而若采用非递归方法实现三种遍历,则要用栈来模拟实现(递归也是用栈实现的)。下面先简要介绍三种遍历方式的递归实现,再详细介绍三种遍历方式的非递归实现 一、三种遍历方式的递归实现(比较简单,这里不详细讲解) 1、先序遍历——按照“根节点-左孩子-右孩子”的顺序进行访问 1 /** 2 * Definition for binary tree 3 * struct TreeNode { 4 * int val; 5 * TreeNode *left; 6 * TreeNode *right; 7 * TreeNode(int x) : val(x), left(NULL), right(NULL) {} 8 * }; 9 */ 10 class Solution {

详解二叉树的非递归遍历

五迷三道 提交于 2019-12-16 17:26:45
本文转载自: http://blog.csdn.net/zhangxiangdavaid/article/details/37115355 前言   对于二叉树的递归遍历比较简单,所以本文主要讨论的是非递归版。其中,中序遍历的非递归写法最简单,后序遍历最难。    节点的定义: //Binary Tree Node typedef struct node { int data; struct node* lchild; //左孩子 struct node* rchild; //右孩子 }BTNode;   首先,有一点是明确的:非递归写法一定会用到栈,这个应该不用太多的解释。我们先看中序遍历: 中序遍历 分析   中序遍历的递归定义:先左子树,后根节点,再右子树。如何写非递归代码呢?一句话:让代码跟着思维走。我们的思维是什么?思维就是中序遍历的路径。假设,你面前有一棵二叉树,现要求你写出它的中序遍历序列。如果你对中序遍历理解透彻的话,你肯定先找到左子树的最下边的节点。那么下面的代码就是理所当然的: 中序代码段(i) BTNode* p = root; //p指向树根 stack<BTNode*> s; //STL中的栈 //一直遍历到左子树最下边,边遍历边保存根节点到栈中 while (p) { s.push(p); p = p->lchild; }  

二叉树结构的建立与遍历

坚强是说给别人听的谎言 提交于 2019-12-14 07:50:24
#include <stdio.h> #include <stdlib.h> #define MAX_LEN 50 /*二叉树的二叉链表结构*/ typedef struct node { struct node *lchild; struct node *rchild; char data; }BTREE; /*栈的数组实现*/ typedef struct { int top; BTREE *a[MAX_LEN]; //结构体数组,每个元素均为一个结点 }Stack; /*队列的数组实现*/ typedef struct { BTREE *a[MAX_LEN]; //结构体数组,每个元素均为一个结点 int front; int rear; }Queue; /*为栈分配空间*/ Stack *Createstack() { Stack *p; p = (Stack *)malloc(sizeof(Stack)); p->top = -1; return p; } /*为队列分配空间*/ Queue *Createqueue() { Queue *p; p = (Queue *)malloc(sizeof(Queue)); p->front = 0; p->rear = 0; return p; } /*菜单*/ int Menu() { int x; printf("\n\n"

数据结构之树

时光怂恿深爱的人放手 提交于 2019-12-14 07:26:28
数据结构之树(含代码) 树的基本概念 子树的个数没有限制,但它们一定是互不相交的 树的结点包含一个数据元素及若干指向其子树的分支;结点拥有的子树数称为结点的度;度为0的结点称为叶结点或终端结点;度不为0的结点称为非终端结点或分支结点;除根结点之外,分支结点也称为内部结点;树的度是树内各结点的度的最大值。 结点的层次从根开始定义起;树中结点的最大层次称为树的深度或高度; 如果将树中结点的各子树看成从左至右是有次序的,不能互换的,则称该树为有序树,否则称为无序树 双亲表示法 每个结点都有data和left,right,data是数据,存储结点的数据信息;而lef,rig是指针,存储该结点的双亲在数组中的下标;根结点没有双亲,所以指针域为-1; 二叉树 二叉树是n个结点的有限集合,该集合或者为空集,或者由一个根结点和两棵互不相交的、分别成为根结点的左子树和右子树的二叉树组成 二叉树的特点: 每个结点最多有两棵子树,所以二叉树中不存在度大于2的结点 左子树和右子树是有顺序的,次序不能任意颠倒 即使树中某结点只有一棵子树,也要区分它是左子树还是右子树 满二叉树:在一棵二叉树中,如果所有分支结点都存在左子树和右子树,并且所有叶子都在同一层上 特点: 叶子只能出现在最下一层 非叶子结点的度一定是2 在同样深度的二叉树中,满二叉树的结点个数最多,子树最多 完全二叉树

二叉树的遍历

醉酒当歌 提交于 2019-12-14 05:43:16
1.前序遍历 1.递归 /** * 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 { vector < int > re ; public : vector < int > preorderTraversal ( TreeNode * root ) { if ( root ) { re . push_back ( root - > val ) ; preorderTraversal ( root - > left ) ; preorderTraversal ( root - > right ) ; } return re ; } } ; 2.迭代 (1) 1.根节点入栈,出栈。 2.右子树先入栈,然后左子树入栈。 3.栈顶元素出栈 /** * Definition for a binary tree node. * struct TreeNode { * int val; * TreeNode *left; * TreeNode *right; * TreeNode