刷题计划 dya13 二叉树(二)【二叉树的层序遍历】【翻转二叉树】

⚡刷题计划day13 二叉树(二)继续,任务2道例题然后还有10道类似题,可以点个免费的赞哦~

往期可看专栏,关注不迷路,

您的支持是我的最大动力🌹~

102.二叉树的层序遍历

上一小节我们练习遍历的其实也是深度优先遍历,而接下来我们会介绍二叉树的另一种遍历方式:层序遍历,对应就是图论中的广度优先遍历

  1. 二叉树的层序遍历

(https://leetcode.cn/problems/binary-tree-level-order-traversal/description/)

法一:队列

我们之前迭代遍历是用栈先进后出模拟深度优先遍历,同样对于层序遍历可以使用队列先进先出的逻辑来模拟。

辅助理解动画如下,详细见代码注释:

public void bfs2(TreeNode node) {
    // 如果根节点为空,直接返回
    if (node == null) return;
​
    // 创建一个队列,用于存储待遍历的节点
    Queue<TreeNode> que = new LinkedList<TreeNode>();
    // 将根节点加入队列
    que.offer(node);
​
    // 循环直到队列为空,即所有节点都被访问过
    while (!que.isEmpty()) {
        // 创建一个列表,用于存储当前层的节点值
        List<Integer> itemList = new ArrayList<Integer>();
        // 获取当前队列的大小,即当前层的节点数
        int len = que.size();
​
        // 循环处理当前层的所有节点
        while (len > 0) {
            // 从队列头部取出一个节点
            TreeNode tmpNode = que.poll();
            // 将节点的值添加到当前层的列表中
            itemList.add(tmpNode.val);
​
            // 如果节点的左子节点不为空,将其加入队列
            if (tmpNode.left != null) que.offer(tmpNode.left);
            // 如果节点的右子节点不为空,将其加入队列
            if (tmpNode.right != null) que.offer(tmpNode.right);
            // 当前层的节点数减一
            len--;
        }
​
        // 当前层的所有节点处理完毕后,将节点值列表添加到结果列表中
        resList.add(itemList);
    }
}

法二:递归

关于递归逻辑上期有讲,主要注意三个要素即可:

1.确定递归函数的参数和返回值

2.确定终止条件

3.确定单层递归的逻辑

AC代码及注释如下:

class Solution {
​
   List<List<Integer>> resList = new ArrayList<List<Integer>>();
    public List<List<Integer>> levelOrder(TreeNode root) {
        bfs1(root,0);
       return resList;
    }
    
    public void bfs1(TreeNode node,Integer deep){
      if(node == null) return;
      deep++;
​
      if(resList.size()<deep){
      //当层级增加时,list的Item也增加,利用list的索引值进行层级界定
         List<Integer> item = new ArrayList<>();
         resList.add(item);
      }
      // 将当前节点的值添加到对应层级的列表中
      resList.get(deep-1).add(node.val);
​
      bfs1(node.left,deep);
      bfs1(node.right,deep);
   }
}

有兴趣的,可以直接拿下这十道题:

学会二叉树的层序遍历,可以一口气打完以下十题:

226.翻转二叉树

  1. 翻转二叉树

(https://leetcode.cn/problems/invert-binary-tree/description/)

如图翻转,也是很经典的一道题,可以运用我们之前的各种遍历方法实现:

可以发现,把每一个节点的左右孩子交换一下,就可以达到整体翻转的效果。

这道题目使用前序遍历和后序遍历都可以,唯独中序遍历不方便,因为中序遍历会把某些节点的左右孩子翻转了两次!建议拿纸画一画,就理解了

那么层序遍历可以不可以呢?依然可以的!只要把每一个节点的左右孩子翻转一下的遍历方式都是可以的!

废话不多说,上代码!

法一:层序遍历法(bfs)

class Solution {
​
    public TreeNode invertTree(TreeNode root) {
        if(root==null) return null;
        Queue<TreeNode> queue = new LinkedList<>();
        queue.offer(root);
​
        while (!queue.isEmpty()){
            int size = queue.size();
            for (int i=0;i<size;i++){
                TreeNode tmpNode = queue.poll();
                swap(tmpNode);
                if(tmpNode.left!=null) queue.offer(tmpNode.left);
                if (tmpNode.right!=null) queue.offer(tmpNode.right);
            }
        }
        return root;
    }
​
    public void swap(TreeNode node){
        TreeNode temp = node.left;
        node.left = node.right;
        node.right = temp;
    }
​
}

法二:迭代遍历(dfs)

前后序遍历都可以

中序不行,因为先左孩子交换孩子,再根交换孩子(做完后,右孩子已经变成了原来的左孩子),再右孩子交换孩子(此时其实是对原来的左孩子做交换)

class Solution {
​
    public TreeNode invertTree(TreeNode root) {
        if(root==null) return null;
        swap(root);
        invertTree(root.left);
        invertTree(root.right);
        return root;
​
    }
    public void swap(TreeNode node){
        TreeNode tmp = node.left;
        node.left = node.right;
        node.right = tmp;
    }
}

欢迎点赞收藏关注~

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值