前端算法小白攻略39-leetcode(二叉树最大宽度)

156 阅读3分钟

「这是我参与2022首次更文挑战的第22天,活动详情查看:2022首次更文挑战

前言

今天我们要求解的是二叉树的最大宽度,其实就是求二叉树最宽的边界是多少,转化为两端之差即可,直接看题

题目描述

662. 二叉树最大宽度

给定一个二叉树,编写一个函数来获取这个树的最大宽度。树的宽度是所有层中的最大宽度。这个二叉树与满二叉树(full binary tree)结构相同,但一些节点为空。

每一层的宽度被定义为两个端点(该层最左和最右的非空节点,两端点间的null节点也计入长度)之间的长度。

来源:力扣(LeetCode) 链接:leetcode-cn.com/problems/ma… 著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

解题思路

先看题给的三个例子,我们来说明一下以便思考

image.png 其实节点的值多少与我们无关,重要的是它们的位置,那么我们现在给所有的节点按层序遍历的方式加上序号来看看最大宽度是什么:
注意:如果两端有节点,中间的null值也会计入,所以我们也把此时的null标上序号,我们这里以例1中的近似满二叉树的结构做标记,另外两个例子也可以用我们得出的规则进行构造。

image.png 标记序号二叉树中,我们能够发现,从根节点1往下,每一层左节点的序号是它父节点的2倍,右节点的序号是它父节点的2倍加1

思路转化

求出每一层的的节点序号,用最右边节点的序号减去最左边节点的序号再加1就是每一层的宽度,那么我们就可以知道哪个层级宽度是最大的了

开始解题

这里数字加n代表bigInt类型,是用做大数值运算的,由于本题数据量比较大所以得加上,不加会报错哦

var widthOfBinaryTree = function (root) { 
    if (!root) return 0; 
    
    // 如果root不为空那么至少有1个根节点,最大宽度我们设初始值为1n
    // que是我们定义的一个二维数组,0n表示我们当前层第1个节点的序号,root表示当前层的节点
    let max= 1n, que = [[0n, root]]; 
    
    while (que.length) { 
    
        // 在每次循环前求解一下上一层的宽度与max比较如果大于就把值赋给max
        // width就是que中最后一个节点序号(右端点)减去第一个节点序号(左端点)再加1
        const width = que[que.length - 1][0] - que[0][0] + 1n; 
        if (width > max) max= width; 
        
        // 初始化赋值一个临时数组来存放下一层的所有节点组成的二维数组
        let temp= []; 
        for (const [i, q] of que) {
            // 这里的q是下一层节点q.left、q.right的父节点,所以应用我们的序号规则即可
            q.left && temp.push([i * 2n, q.left]); 
            q.right && temp.push([i * 2n + 1n, q.right]); 
        }
        que = temp; // 遍历到最后一层时,下一层为空,temp为[]
    }
    return max; 
};