剑指 Offer 32 - II. 从上到下打印二叉树 II——利用队列层序遍历BFS

(一)

原题链接

从上到下打印出二叉树的每个节点,同一层的节点按照从左到右的顺序打印。

例如:
给定二叉树: [3,9,20,null,null,15,7]

返回:

[3,9,20,15,7]

提示:

节点总数 <= 1000


解法:利用队列层序遍历

思路
  1. 将头结点入队列
  2. 记录当前队列的长度n
  3. 从队头出一个结点,并将其值加入到数组内,再判断其左右结点是否为空,如果不为空则加入队列,此步骤执行n次
  4. 重复步骤2,3直到队列为空为止
特殊情况

如果root为空,返回一个空数组

代码
public int[] levelOrder(TreeNode root) {
    Queue<TreeNode> queue = new LinkedList<TreeNode>();
    if(root == null) return new int[0];
    List<Integer> list = new ArrayList<>();
    queue.add(root);
    while (!queue.isEmpty()){
        // 将上一层的结点出队,并且将他们的左右孩子结点入队
        for (int i = queue.size(); i > 0; --i) {
            TreeNode temp = queue.poll();
            list.add(temp.val);
            if(temp.left != null) queue.add(temp.left);
            if(temp.right != null) queue.add(temp.right);
        }
    }
    int n = list.size();
    // ArrayList<Integer> 转换为 int数组,因为Integer数组不能直接转换为int,因此需要遍历
    int[] result = new int[n];
    for (int i = 0; i < n; i++) {
        result[i] = list.get(i);
    }
    return result;
}
提交结果

(二)

原题链接

从上到下按层打印二叉树,同一层的节点按从左到右的顺序打印,每一层打印到一行。

例如:
给定二叉树: [3,9,20,null,null,15,7],

返回其层次遍历结果:

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

限制

节点总数 <= 1000


解法:利用队列特性层序遍历

思路

和(一)的思路一样,区别在于返回时将每一层的结点分别开来

那么相应的,执行步骤3时,新建一个数组,用来存放当前层的结点值,当前层遍历完成后,将数组加入到List中

特殊情况

如果root为空,返回一个空数组

代码
public List<List<Integer>> levelOrder(TreeNode root) {
    List<List<Integer>> result = new LinkedList<>();
    // 先进先出
    Queue<TreeNode> queue = new LinkedList<>();
    if(root == null) return result;
    // 首先根节点入队
    queue.add(root);
    // 当前层的结点个数(因为第一层只有根结点,所以是1),下一层的结点个数
    int currCount = 1, nextCount;
    while (!queue.isEmpty()){
        // 下一层个数初始为0;
        nextCount = 0;
        // 存储当前层的结点数值
        List<Integer> currNum = new LinkedList<>();
        // 遍历当前层结点,看是否有子结点,如果有就入队,并且下一层的结点数加一
        for (int i = 0; i < currCount; i++) {
            // 出队列
            TreeNode temp = queue.poll();
            currNum.add(temp.val);
            // 如果左右不空,则入队
            if(temp.left != null){
                queue.add(temp.left);
                ++nextCount;
            }
            if(temp.right != null){
                queue.add(temp.right);
                ++nextCount;
            }
        }
        // 增加一层
        result.add(currNum);
        // 下一层变为当前层
        currCount = nextCount;
    }
    return result;
}
提交结果

(三)

原题链接

请实现一个函数按照之字形顺序打印二叉树,即第一行按照从左到右的顺序打印,
第二层按照从右到左的顺序打印,第三行再按照从左到右的顺序打印,其他行以此类推。

例如:
给定二叉树: [3,9,20,null,null,15,7]

返回其层次遍历结果:

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

提示:

节点总数 <= 1000


解法:层序遍历

思路

同(二)的区别在于,偶数层需要逆序

借助双端队列,如果当前是奇数层,那么数值依次加入到队尾

如果当前层是偶数层,那么数值依次加入到队头

特殊情况

根节点为空

代码
public List<List<Integer>> levelOrder(TreeNode root) {
    List<List<Integer>> result = new ArrayList<>();
    if(root == null) return result;
    Queue<TreeNode> queue = new LinkedList<>();
    queue.add(root);
    int m = 1;
    while (!queue.isEmpty()){
        LinkedList<Integer>list = new LinkedList<>();
        for (int i = queue.size(); i > 0 ; --i) {
            TreeNode temp = queue.poll();
            // 如果为奇数层,将数值加入到链表尾部,偶数层则加入到头部
            if((m & 1) == 1) list.addLast(temp.val);
            else list.addFirst(temp.val);
            if(temp.left != null) queue.add(temp.left);
            if(temp.right != null) queue.add(temp.right);
        }
        // 层数加一
        ++m;
        result.add(list);
    }
    return result;
}
提交结果

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值