前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >二叉树问题(二)-LeetCode 965、563、993、958、919(树深度,层次遍历)

二叉树问题(二)-LeetCode 965、563、993、958、919(树深度,层次遍历)

作者头像
算法工程师之路
发布2019-12-24 17:29:44
3530
发布2019-12-24 17:29:44
举报
文章被收录于专栏:算法工程师之路

作者:TeddyZhang,公众号:算法工程师之路

二叉树问题(二):

LeetCode # 965 563 993 958 919

1

编程题

【LeetCode #965】单值二叉树

如果二叉树每个节点都具有相同的值,那么该二叉树就是单值二叉树。 只有给定的树是单值二叉树时,才返回 true;否则返回 false。

(迭代法,中序遍历)

代码语言:javascript
复制
class Solution {
public:
    bool isUnivalTree(TreeNode* root) {
        stack<TreeNode*> sta;
        TreeNode* pre = nullptr;
        TreeNode* cur = root;
        while(cur != nullptr || !sta.empty()) {
            if(cur != nullptr) {
                sta.push(cur);
                cur = cur->left;
            }else {
                cur = sta.top();
                sta.pop();
                if (pre && pre->val != cur->val) {
                    return false;
                }
                pre = cur;
                cur = cur->right;
            }
        }
        return true;
    }
};

(递归法)

代码语言:javascript
复制
class Solution {
public:
    bool isUnivalTree(TreeNode* root) {
        if (root == nullptr) return true;
        if (root->left && root->left->val != root->val) {
            return false;
        }
        if (root->right && root->right->val != root->val) {
            return false;
        }
        return isUnivalTree(root->left) && isUnivalTree(root->right);
    }
};

来源:力扣(LeetCode) 链接:https://leetcode-cn.com/problems/univalued-binary-tree/

【LeetCode #563】二叉树的坡度

给定一个二叉树,计算整个树的坡度。

一个树的节点的坡度定义即为,该节点左子树的结点之和和右子树结点之和的差的绝对值。空结点的的坡度是0。 整个树的坡度就是其所有节点的坡度之和。

示例: 输入: 1 / \ 2 3 输出: 1 解释: 结点的坡度 2 : 0 结点的坡度 3 : 0 结点的坡度 1 : |2-3| = 1 树的坡度 : 0 + 0 + 1 = 1

解题思路:

首先我们写出一个计算一个二叉树中子树的节点和的递归式子,然后再递归参数中使用count来累加两个子树节点和的差值,最后返回count即可。注意使用引用传递而不是值传递。

代码语言:javascript
复制
/**
 * 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:
    int add(TreeNode* node, int& count) {
        if(node == nullptr) return ;
        int left = add(node->left, count);
        int right = add(node->right, count);
        count += abs(left - right);
        return left+right+node->val;
    }
    int findTilt(TreeNode* root) {
        int res = ;
        add(root, res);
        return res;
    }
};

来源:力扣(LeetCode) 链接:https://leetcode-cn.com/problems/binary-tree-tilt

【LeetCode #993】二叉树的堂兄节点

在二叉树中,根节点位于深度 0 处,每个深度为 k 的节点的子节点位于深度 k+1 处。 如果二叉树的两个节点深度相同,但父节点不同,则它们是一对堂兄弟节点。 我们给出了具有唯一值的二叉树的根节点 root,以及树中两个不同节点的值 x 和 y。 只有与值 x 和 y 对应的节点是堂兄弟节点时,才返回 true。否则,返回 false

解题思路:

使用pair类型储存对应x节点以及y节点的深度和父节点的值,然后进行比较即可。 注意该二叉树中的值都是唯一的,没有重复的。

代码语言:javascript
复制
/**
 * 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:
    void find(TreeNode* node, int val, int dep, int par, pair<int, int>& res) {
        if (node == nullptr) return;
        if (node->val == val) {
            res.first = dep;
            res.second = par;
            return;
        } else {
            find(node->left, val, dep+, node->val, res);
            find(node->right, val, dep+, node->val, res);
        }
    }
    bool isCousins(TreeNode* root, int x, int y) {
        pair<int, int> res1, res2;
        find(root, x, , -1, res1);  // 根节点的父节点值设为-1
        find(root, y, , -1, res2);
        return (res1.first == res2.first) && (res1.second != res2.second);
    }
};

来源:力扣(LeetCode) 链接:https://leetcode-cn.com/problems/cousins-in-binary-tree

【LeetCode #958】二叉树的完全性检验(完全二叉树)

给定一个二叉树,确定它是否是一个完全二叉树。 百度百科中对完全二叉树的定义如下: 若设二叉树的深度为 h,除第 h 层外,其它各层 (1~h-1) 的结点数都达到最大个数,第 h 层所有的结点都连续集中在最左边,这就是完全二叉树。(注:第 h 层可能包含 1~ 2h 个节点。)

解题思路:

使用类似层次遍历的方法,使用flag标记遇到了nullptr,然后置为true,接着判断当flag=true时,接下来访问的节点是否为空,如果都为空,则说明是完全二叉树,否则不是。 注意:为了将stack中加入nullptr,因此只判断tmp是否为空即可!

代码语言:javascript
复制
/**
 * 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:
    bool isCompleteTree(TreeNode* root) {
        bool flag = false;  
        queue<TreeNode*> que;
        que.push(root);
        while(!que.empty()) {
            TreeNode* tmp = que.front();
            que.pop();
            if (tmp == nullptr) flag = true;
            if (flag && tmp) return false;  // 遇到nullptr,后面都应该是nullptr  
            if (tmp) {   // 与层次遍历不同,只需要判断tmp是否为nullptr
                que.push(tmp->left);
                que.push(tmp->right);
            }
        }
        return true;
    }
};

来源:力扣(LeetCode) 链接:https://leetcode-cn.com/problems/check-completeness-of-a-binary-tree

【LeetCode #919】完全二叉树插入器

完全二叉树是每一层(除最后一层外)都是完全填充(即,结点数达到最大)的,并且所有的结点都尽可能地集中在左侧。 设计一个用完全二叉树初始化的数据结构 CBTInserter,它支持以下几种操作:

CBTInserter(TreeNode root) 使用头结点为 root 的给定树初始化该数据结构; CBTInserter.insert(int v) 将 TreeNode 插入到存在值为 node.val = v 的树中以使其保持完全二叉树的状态,并返回插入的 TreeNode 的父结点的值; CBTInserter.get_root() 将返回树的头结点。

解题思路:

LeetCode上的翻译很烂,简单来说,就是现在有一颗root为根节点的完全二叉树,当我们向二叉树中插入节点的,也应该保证完全二叉树的性质,这在里面使用层次遍历的方法,寻找某个节点的左节点或者右节点为nullptr的节点,定为待插入节点root_. 注意如果向某个节点的右节点插入了一个节点,那么待插入节点root_会发生变化!

代码语言:javascript
复制
/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
 * };
 */
class CBTInserter {
public:
    queue<TreeNode*> que;
    // 注意root为一个完全二叉树
    CBTInserter(TreeNode* root) : root_(root), node_(nullptr) {
        que.push(root_);
        while(!que.empty()) {
            TreeNode* tmp = que.front();
            que.pop();
            if (tmp->left)  que.push(tmp->left);
            if (tmp->right) que.push(tmp->right);
            if (node_ == nullptr && (tmp->left == nullptr || tmp->right == nullptr)) {
                node_ = tmp;
                break;
            }
        }
    }

    int insert(int v) {
        TreeNode* newNode = new TreeNode(v);
        int father = node_->val;
        if(node_->left == nullptr) node_->left = newNode;
        else {
            node_->right = newNode;
            if (!que.empty()) {
                node_ = que.front();
                que.pop();
            } 
        }  
        return father;
    }

    TreeNode* get_root() {
        return root_;
    }
private:
    TreeNode* node_;   // 用来储存待插入节点的位置
    TreeNode* root_;   // 用来储存树根节点的位置
};

来源:力扣(LeetCode) 链接:https://leetcode-cn.com/problems/complete-binary-tree-inserter

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2019-12-19,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 算法工程师之路 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档