后序遍历

二叉树

牧云@^-^@ 提交于 2020-01-18 23:36:19
二叉树 二叉树的概念 定义:每个节点最多只能有两个子节点的一种形式称之为二叉树 二叉树的节点分为左节点和右节点 图示: 满二叉树:二叉树的所有叶子节点(无分叉的节点)都在最后一层,并且总结点数为2 n - 1,n为层数 图示: 完全二叉树:所有的叶子节点都在最后一层或者是倒数第二层,并且最后一层左边连续,倒数第二层右边连续。连续就是都是这一层的。 图示: 二叉树的遍历方式 基本概念 前序遍历:先输出父节点,在遍历左子树和右子树 中序遍历:先遍历左子树,在输出父节点,在遍历右子树 后序遍历:先遍历左子树,再遍历右子树,最后输出父节点 ** 父节点的输出先后决定其实遍历的顺序** 思路分析 创建一个二叉树 遍历: 前序遍历: 输出当前节点 判断:如果左子节点不为空,那就继续前序遍历 判断:如果右子节点不为空,那就继续前序遍历 中序遍历: 如果当前节点的左子节点不为空,则递归中序遍历 输出当前节点 如果当前节点右子节点不为空,那就递归中序遍历 后序遍历: 如果当前节点的左子节点不为空,那就递归左子节点 如果当前节点的右子节点不为空,那就递归右子节点 输出当前节点 代码实现: class BinaryTree { //二叉树有必须有根节点 private HeroNode root ; public BinaryTree ( HeroNode root ) { this . root =

23-二叉搜索树的后序遍历序列

谁说我不能喝 提交于 2020-01-18 22:44:29
输入一个整数数组,判断该数组是不是某二叉搜索树的后序遍历的结果。如果是则输出Yes,否则输出No。假设输入的数组的任意两个数字都互不相同。 二叉搜索树:若它的左子树不空,则左子树上所有结点的值均小于它的根结点的值; 若它的右子树不空,则右子树上所有结点的值均大于它的根结点的值; 1.后续遍历我们可以知道,最右边的是根节点r。 2.通过根节点r我们可以判断左子树和右子树。 3.判断左子树中的每个值是否小于r,右子树的每个值是否大于r. 4.对左、右子树递归判断。 // 递归版 function VerifySquenceOfBST ( sequence ) { // write code here if ( sequence . length == 0 ) return false ; return isSquence ( sequence , 0 , sequence . length - 1 ) } function isSquence ( squence , start , end ) { if ( start >= end ) return true ; var i = start ; while ( i < end && squence [ i ] < squence [ end ] ) { i ++ ; } for ( var j = i ; j < end ; j ++

102. 二叉树的层次遍历

时光总嘲笑我的痴心妄想 提交于 2020-01-18 04:01:05
非递归算法: 用队列,关键是对入队的结点进行划分,计算当前层次的结点总数; 一,下一层的结点总数的计算: 法一: 从上一层第一个结点开始出队到上一层最后一个结点出对完成时,下一层所有结点刚好完成了入队操作;在此段时间内不断更新计数器可计算出下一层的节点总数;此时用下一层结点总数更新当前结点总数值; 法二: 外层每一次循环(while(){})都是一层,所以直接在外层调用 queue.size()即为当前层次结点的总数; 二,List<List>类型(以线性表为元素的线性表)的集合的操作; 声明:List<List> list = new ArrayList<List< Integer >>(); 添加外层表的元素:list.add(new ArrayList()); 添加表的表的元素(整型值)list.get(level).add(tmp.val); 三,队列的使用 声明:Queue queue = new LinkedList(); 入队:queue.add(root); 出队:tmp = queue.remove(); 判断队空:queue.isEmpty() /** * Definition for a binary tree node. * public class TreeNode { * int val; * TreeNode left; * TreeNode

递归 VS 非递归 内涵

空扰寡人 提交于 2020-01-16 05:13:08
递归与非递归转换的基础知识是能够正确理解三种树的遍历方法:前序,中序和后序,第一篇就是关于这三种遍历方法的递归和非递归算法。 一、为什么要学习递归与非递归的转换的实现方法? 1)并不是每一门语言都支持递归的。 2)有助于理解递归的本质。 3)有助于理解栈,树等数据结构。 二、三种遍历树的递归和非递归算法 递 归与非递归的转换基于以下的原理:所有的递归程序都可以用树结构表示出来。需要说明的是,这个”原理”并没有经过严格的数学证明,只是我的一个猜 想,不过在至少在我遇到的例子中是适用的。学习过树结构的人都知道,有三种方法可以遍历树:前序,中序,后序。理解这三种遍历方式的递归和非递归的表达方 式是能够正确实现转换的关键之处,所以我们先来谈谈这个。需要说明的是,这里以特殊的二叉树来说明,不过大多数情况下二叉树已经够用,而且理解了二叉树的 遍历,其它的树遍历方式就不难了。 1)前序遍历 a)递归方式: void preorder_recursive(Bitree T) /* 先序遍历二叉树的递归算法 */ { if (T) { visit(T); /* 访问当前结点 */ preorder_recursive(T->lchild); /* 访问左子树 */ preorder_recursive(T->rchild); /* 访问右子树 */ } } b)非递归方式 void preorder

二叉树的后序遍历

独自空忆成欢 提交于 2020-01-16 03:59:06
/** * Definition of TreeNode: * class TreeNode { * public: * int val; * TreeNode *left, *right; * TreeNode(int val) { * this->val = val; * this->left = this->right = NULL; * } * } */ class Solution { public:   /*   * @param root: A Tree   * @return: Postorder in ArrayList which contains node values.   */   vector <int> v;   vector<int> postorderTraversal(TreeNode * root) {   if (root == NULL) {     return v;   }   postorderTraversal(root->left);   postorderTraversal(root->right);   v.push_back(root->val);   return v;   } }; 来源: https://www.cnblogs.com/ye-chen/p/7543247.html

二叉树的建立与遍历(简单操作)

亡梦爱人 提交于 2020-01-14 11:18:49
Description 已知一个按先序序列输入的字符序列,如abc,de,g,f,(其中逗号表示空节点)。请建立二叉树并按中序和后序方式遍历二叉树,最后求出叶子节点个数和二叉树深度。 <o:p></o:p> Input 输入一个长度小于50个字符的字符串。 Output 输出共有4行: 第1行输出中序遍历序列; 第2行输出后序遍历序列; <o:p></o:p>第3行输出叶子节点个数; <o:p></o:p>第4行输出二叉树深度。<o:p></o:p> Sample Input abc,de,g,f, Output cbegdfa cgefdba 3 5 ————————————————————————————————————— 先序遍历,中序遍历,后序遍历 思想一样,只是顺序不同 二叉树高度计算 递归解法: (1)如果二叉树为空,二叉树的深度为0 (2)如果二叉树不为空,二叉树的深度 = max(左子树深度, 右子树深度) + 1 ———————————————————————————————————— # include <bits/stdc++.h> using namespace std ; struct node { char data ; struct node * lt ; //指向根的左子树 struct node * rt ; //指向根的右子树 } ; char

二叉树的后序遍历

流过昼夜 提交于 2020-01-14 08:34:46
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 /** * 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 { public : vector< int > postorderTraversal(TreeNode* root) { vector< int > path; postOrder(root, path); return path; } /* void postOrder(TreeNode* root, vector<int> &path) { //递归写法 if (root) { postOrder(root->left, path); postOrder(root->right, path); path.push

二叉树的后序遍历

假如想象 提交于 2020-01-14 00:55:07
如下图表示一颗二叉树,对它进行先序遍历操作,采用两种方法,递归和非递归操作。。 遍历结果为:4526731。。 1、递归操作: 思想:若二叉树为空,返回。否则 1)后序遍历右子树;2)后序遍历左子树;3)遍历根节点 代码: void PostOrder(BiTree root) { if(root==NULL) return ; PostOrder(root->lchild); //递归调用,后序遍历左子树 PostOrder(root->rchild); //递归调用,后序遍历右子树 printf("%c ", root->data); //输出数据 } 2、非递归操作 代码: void PostOrder_Nonrecursive(BiTree T) // 后序遍历的非递归 { stack<BiTree> S; BiTree curr = T ; // 指向当前要检查的节点 BiTree previsited = NULL; // 指向前一个被访问的节点 while(curr != NULL || !S.empty()) // 栈空时结束 { while(curr != NULL) // 一直向左走直到为空 { S.push(curr); curr = curr->lchild; } curr = S.top(); // 当前节点的右孩子如果为空或者已经被访问,则访问当前节点

二叉树递归遍历(前序,中序,后序)

谁都会走 提交于 2020-01-13 02:31:25
1.Java 中没有 Tree 的数据结构,不过我们可以自己写一个: public class TreeNode { int val; TreeNode left; TreeNode right; public TreeNode(int val) { this.val = val; } public TreeNode(int val, TreeNode left, TreeNode right) { this.val = val; this.left = left; this.right = right; } } 2.初始化遍历的树 . TreeNode t4=new TreeNode(4,null,null); TreeNode t8=new TreeNode(8,null,null); TreeNode t6=new TreeNode(6,t4,t8); TreeNode t12=new TreeNode(12,null,null); TreeNode t16=new TreeNode(16,null,null); TreeNode t14=new TreeNode(14,t12,t16); TreeNode t10=new TreeNode(10,t6,t14); 3.前序遍历 public static void preOrder(TreeNode treeNode){

python-迭代器模式

风流意气都作罢 提交于 2020-01-12 09:09:53
源码地址: https://github.com/weilanhanf/PythonDesignPatterns 说明: 集合是用来管理和组织数据对象的数据结构的。集合有两项基本职能:一、批量的存储数据对象,二、在不暴露集合内部结构的条件下向外界提供访问内部元素的接口(可能存在的遍历方式:顺序、逆序遍历,二叉树的广度优先,先序后序中序遍历等)。要使得集合保持整洁和优雅,而不是说令集合内部包含着各种遍历的方法。因此要求将遍历的方法从集合的指责中分离出来,按照不同的遍历需求分别封装成一个个专门遍历集合内部数据的迭代器。这种思想可以最大限度的减少彼此之间的耦合程度,从而建立一个松散耦合的对象网络。职责分离的要点就是要对分离的职责进行封装,并以抽象对象的方式建立彼此之间的关系。 迭代器模式:提供一种方法顺序访问一个聚合对象中各个元素,且不用暴露该对象的内部表示 聚合对象的两个职责: 存储数据,聚合对象的基本职责 遍历数据,既是可变化的,又是可分离的。将遍历数据的行为从聚合对象中分离出来,封装在迭代器对象中。由迭代器来提供遍历聚合对象内部数据的行为,简化聚合对象的设计,更符合单一职责原则。 迭代器模式包含以下4个角色: Iterator(抽象迭代器) ConcreteIterator(具体迭代器) Aggregate(抽象聚合类) ConcreteAggregate(具体聚合类) 实例: