美文网首页
javaScript构建对称二叉树

javaScript构建对称二叉树

作者: 晨风扶绿的芭蕉 | 来源:发表于2020-04-29 20:18 被阅读0次

       在讲二叉树之前,应该先了解数据结构中关于树的定义:(维基百科)。其中比较重要的常用术语:节点父节点叶子。而二叉树并不是树的特殊情况,因为二叉树和树的定义并不重合,二叉树并不是树的子集。只是二叉树类似树的结构而已。二叉树的定义:二叉树。二叉树比较重要的常用术语:左子树、右子树、根节点、满二叉树完全二叉树。这些概念比较多比较杂,需要花时间好好理解一下。

      今天我要写的是用JavaScript构建满二叉树(再进一步通过二叉树,判断二叉树是否是相同的树(leetcode),或者是否是对称二叉树(leetcode)。二叉树是数据结构与算法中非常重要的一部分,同时也是比较难理解的部分。(我也是通过慢慢理解,自己琢磨,多做笔记,多动手,渐渐消化它的。代码部分尽量讲的详细通俗一点。)

我们假设使用数组来表示二叉树的存储结构(链表也可以,这里使用数组更加方便)

使用es6构建树的节点,添加属性(val, left,right)

这一步的主要作用就是创建二叉树的节点属性。以后二叉树的节点都靠这个函数生成,生成的new Node就全都直接拿来只用。

第二步就开始创建二叉树,这一步有点抽象,需要仔细研读下代码。

通过class,创建二叉树

代码里面的含义,容我一步步解析:(es6中class的语法和constructor我就不细讲怎么使用了)

首先创建一个空数组,用来保存二叉树中所有的节点。那么肯定得先生成二叉树的节点,所以就用到for循环来创建所有节点,并存进数组当中。这里的i是数组的索引,我们的思路是通过数组的索引,找到当前索引对应的节点、当前索引所在的深度(层)、当前索引的父节点......

所以这个代码的核心就是利用二叉树中的节点只有两个分支,从而延申出的各种特性。

比如计算n(当前代码所在的层数)就是利用二叉树的特性: 当前索引和所在层级n之间的关系。这里用一张示意图来描述会更加形象一点:

索引和层级N之间的关系图

从图中不难发现,度数(层数)n和索引之间存在的关系:二叉树左侧的索引值  

                                   i = 2 ^(n - 1) - 1

这个也是构建树的关键点。既然   i = 2^(n - 1) - 1,那我们就可以反推出 

该式就是通过当前元素索引计算当前元素所在层数,但是要向下取整

                            即:n = Math.floor(Math.log2(i +1) + 1)

有了这个表达式,我们就可以继续计算出,当前元素所在层数的第一个索引 p:

                            即:  p = Math.pow(2, n -1) -1

继而可以计算出当前索引对应的父节点对应的索引 q:

                            即: q = Math.floor((i - p) / 2) + Math.pow(2, n - 2) - 1

计算父节点的索引的时候,可能有点会迷糊,为什么要把当前位置的索引 i (p为当前层数的第一个索引)减去 p 除以 2 向下取整呢?这就和二叉树的特点又有关系了。因为二叉树中,一个节点对应两个子节点,当前位置索引减去当前层数第一个索引除以2,取整,就是为了计算出父节点相对于父节点那层的第一个索引移动的数值。Math.pow(2, n - 2) - 1这个式子则是上一层的第一索引值,也就是父节点的层数对应的第一个索引值。如果还是不明白,可以自己动手算一算,纸上得来终觉浅

好了,有了这一步,那父节点的索引我们也就知道了。其实到这里二叉树基本已经确定完毕了,下面就是让这棵树散开枝叶了。

这里就可以开始解释,为什么要在计算n层级是,先加入一个判断 i  > 0,因为当索引 i = 0时,它没有父节点,如果你没加判断条件,运行时会报错。parent.left默认初始值都是null,当遍历到node节点时,把它赋值给他的父节点的左子节点。

我们只需要一个根节点root就行了。利用根节点,就可以一层一层的遍历二叉树。最后把保存节点的临时数组的内存释放,返回跟节点,二叉树的构建到此就结束了。当然,你传入一个数组进去,会输出一个对象node,就是数组的头元素,val等于当前元素的值,left,right都是一个对象,left是左节点,里面有左节点的属性,right是有节点,里面有右节点的属性,同时这些属性都是嵌套的,因为我们就是用这种方式构建二叉树的。

我传入的数组是[3,9,20,null,null,15,7]

对应的树的结构:(先序遍历)

[3,9,20,null,null,15,7]

如果你想验证对称二叉树,就需要在里面定义一个方法,判断二叉树是否对称。如果有人看这篇文章的话, 我再写吧。。。。。。估计也就我看看而已,哈哈哈

后面有时间了,再写下二叉树的遍历: 先序遍历(波兰式),中序遍历,后序遍历(逆波兰)

相关文章

  • javaScript构建对称二叉树

    在讲二叉树之前,应该先了解数据结构中关于树的定义:树(维基百科)。其中比较重要的常用术语:节点、父节点、度、...

  • 【LeetCode】101-对称二叉树

    对称二叉树 题目 给定一个二叉树,检查它是否是镜像对称的。 例如,二叉树 [1,2,2,3,4,4,3] 是对称的...

  • LeetCode-101-对称二叉树

    LeetCode-101-对称二叉树 101. 对称二叉树[https://leetcode-cn.com/pro...

  • 2019-04-09 BFS广度优先搜索刷题Day1

    Leetcode 101 对称二叉树 题目描述: 给定一个二叉树,检查它是否是镜像对称的。 例如,二叉树 [1,2...

  • 剑指offer | 对称二叉树

    对称二叉树 请实现一个函数,用来判断一棵二叉树是不是对称的如果一棵二叉树和它的镜像一样,那么它是对称的 分析:根据...

  • 面试题28. 对称的二叉树

    对称的二叉树 题目描述 请实现一个函数,用来判断一棵二叉树是不是对称的。如果一棵二叉树和它的镜像一样,那么它是对称...

  • 第九天的leetcode刷题

    今天的题目是判断是否为对称二叉树:101. 对称二叉树[https://leetcode-cn.com/probl...

  • Swift 对称二叉树 - LeetCode

    题目: 对称二叉树 给定一个二叉树,检查它是否是镜像对称的。 例如,二叉树 [1,2,2,3,4,4,3] 是对...

  • LeetCode 101. 对称二叉树 | Python

    101. 对称二叉树 题目 给定一个二叉树,检查它是否是镜像对称的。 例如,二叉树 [1,2,2,3,4,4,3]...

  • Symmetric Tree对称树

    Easy 判断一棵二叉树是否对称 Example, 二叉树[1,2,2,3,4,4,3] 对称:1/ 2 2/...

网友评论

      本文标题:javaScript构建对称二叉树

      本文链接:https://www.haomeiwen.com/subject/dmzwwhtx.html