题目来源:剑指 Offer 32 - III. 从上到下打印二叉树 III
题目描述
请实现一个函数按照之字形顺序打印二叉树,
即第一行按照从左到右的顺序打印,
第二层按照从右到左的顺序打印,
第三行再按照从左到右的顺序打印,
其他行以此类推。
例如:
给定二叉树: [3,9,20,null,null,15,7],
3
/ \
9 20
/ \
15 7
返回其层次遍历结果:
[
[3],
[20,9],
[15,7]
]
提示:
节点总数 <= 1000
需要注意的是,这一题在层序遍历二叉树时,需要保证奇数层的节点是由左至右正序输出;偶数层的节点由右到左进行倒叙输出;
那么就在第二题的基础上,在奇数/偶数层元素进入集合时,就进行提前判断;若为偶数层,则一直向集合的前面添加,即达到了倒叙的效果
class TreeNode {
int val;
TreeNode left;
TreeNode right;
TreeNode(int x) {
val = x;
}
}
public class Solution {
public List<List<Integer>> levelOrder(TreeNode root) {
//需要注意的是,这次的要求和第二题不太一样,
//在打印时,奇数层 从左至右 顺序输出;偶数层的话需要 从右至左 进行输出;
List<List<Integer>> l1 = new ArrayList<List<Integer>>();
//空树就直接返回空集合;
if (root == null) return l1;
//还是一样的;创建队列存元素;
Queue<TreeNode> queue = new LinkedList<>();
queue.add(root);
//在这里定义一个计数器; 在后面用于区别奇 偶 层;
int count = 0;
//队列不为空就操作;
while (!queue.isEmpty()) {
//注意这里是创建一个集合存入; 集合 l2添加的是 一层,一层遍历的元素;
//且每次循环都会创建一个集合 l2;
List<Integer> l2 = new ArrayList<>();
int num = queue.size();
for (int i = 0; i < num; i++) {
//队头元素出队;存入集合l2;
TreeNode poll = queue.poll();
//若为奇数; 第一层;第三层,第五层....
if(count%2 == 0){
l2.add(poll.val);
}else {
//偶数层;第二层;第四层;第六层.....; 直接让后面出队的节点向前面位置添加;
l2.add(0,poll.val);
}
//判断是否有右子树左子树,若有就存入队列;
if (poll.left != null) queue.add(poll.left);
if (poll.right != null) queue.add(poll.right);
}
//每次取一层存到了集合 l2 ,然后再依次存入总集合 l1;
l1.add(l2);
//计数器加一次;
count++;
}
return l1;
}
}