自学内容网 自学内容网

队列 + 宽搜算法(3)_二叉树最大宽度

个人主页:C++忠实粉丝
欢迎 点赞👍 收藏✨ 留言✉ 加关注💓本文由 C++忠实粉丝 原创

队列 + 宽搜算法(3)_二叉树最大宽度

收录于专栏【经典算法练习
本专栏旨在分享学习算法的一点学习笔记,欢迎大家在评论区交流讨论💌
  

目录

1. 题目链接

2. 题目描述

3. 解法

算法思路:

代战展示:

 


1. 题目链接

OJ链接 ;二叉树最大宽度 icon-default.png?t=O83Ahttps://leetcode.cn/problems/maximum-width-of-binary-tree/

2. 题目描述

给你一棵二叉树的根节点 root ,返回树的 最大宽度 。

树的 最大宽度 是所有层中最大的 宽度 。

每一层的 宽度 被定义为该层最左和最右的非空节点(即,两个端点)之间的长度。将这个二叉树视作与满二叉树结构相同,两端点间会出现一些延伸到这一层的 null 节点,这些 null 节点也计入长度。

题目数据保证答案将会在  32 位 带符号整数范围内。

示例 1:

输入:root = [1,3,2,5,3,null,9]
输出:4
解释:最大宽度出现在树的第 3 层,宽度为 4 (5,3,null,9) 。

示例 2:

输入:root = [1,3,2,5,null,null,9,6,null,7]
输出:7
解释:最大宽度出现在树的第 4 层,宽度为 7 (6,null,null,null,null,null,7) 。

示例 3:

输入:root = [1,3,2,5]
输出:2
解释:最大宽度出现在树的第 2 层,宽度为 2 (3,2) 。

提示:

  • 树中节点的数目范围是 [1, 3000]
  • -100 <= Node.val <= 100

 

3. 解法

算法思路:

利用二叉树的顺序存储 - 通过跟节点的下标, 计算左右孩子的下标:

依旧是利用层序遍历, 但是这一次队列里面不单单存节点信息, 并且还存贮当前节点如果在数组中存储对应的下标(比如我们的堆就是利用数组下标计算左右孩子)

这样我们计算每一层宽度的时候, 无需考虑空节点, 只需将层节点的左右节点的下标相减再加1即可.

 

但是, 这里有一个细节问题 : 如果二叉树的层数非常恐怖的话, 我们任何一种数据类型都不能存下下标的值, 但是没有问题, 因为

1. 我们数据的存储是一个环形结构:

2. 并且题目说明, 数据的范围在int这个类型的最大值范围之内, 因此不会超出一圈;

3. 因此, 如果是求差值的话, 我们无需考虑溢出的情况.

代战展示:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
 * };
 */
class Solution {
public:
    int widthOfBinaryTree(TreeNode* root) 
    {
        vector<pair<TreeNode* , unsigned int>> q;
        if(root == nullptr) return 0;
        q.push_back({root, 1}); 
        unsigned int ret = 0;

        while(q.size())
        {
            int sz = q.size();
            auto [x1, y1] = q[0];
            auto [x2, y2] = q.back();
            ret = max(ret, y2 - y1 + 1);

            vector<pair<TreeNode*, unsigned int>> tmp;
            for(auto [x, y] : q)
            {
                if(x->left) tmp.push_back({x->left, y * 2});
                if(x->right) tmp.push_back({x->right, y * 2 + 1});
            }

            q = tmp;
        }

        return ret;
    }
};


原文地址:https://blog.csdn.net/wer24_25/article/details/143092157

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!