剑指offer32 从上往下打印二叉树
就是层序遍历。
import java.util.ArrayList; import java.util.ArrayDeque; /** public class TreeNode { int val = 0; TreeNode left = null; TreeNode right = null; public TreeNode(int val) { this.val = val; } } */ public class Solution { public ArrayList<Integer> PrintFromTopToBottom(TreeNode root) { ArrayList<Integer> ans = new ArrayList<>(); if(root==null) return ans; ArrayDeque<TreeNode> queue = new ArrayDeque<>(); queue.add(root); while(!queue.isEmpty()){ TreeNode p = queue.remove(); ans.add(p.val); if(p.left!=null) queue.add(p.left); if(p.right!=null) queue.add(p.right); } return ans; } }
运行时间:14ms
占用内存:9164k
# -*- coding:utf-8 -*- # class TreeNode: # def __init__(self, x): # self.val = x # self.left = None # self.right = None class Solution: # 返回从上到下每个节点值列表,例:[1,2,3] def PrintFromTopToBottom(self, root): # write code here if root is None: return [] ans = [] self.levelOrderTraversal(root,ans) return ans def levelOrderTraversal(self,root,ans): queue = [] queue.append(root) while len(queue)>0: node = queue[0] queue.pop(0) ans.append(node.val) if node.left is not None: queue.append(node.left) if node.right is not None: queue.append(node.right)
运行时间:40ms
占用内存:5868k
32b则是分行打印。
多一个分行。
最开始的想法是,加一个HashMap,存每个TreeNode的层数。但是不够优秀。
剑指offer给了优秀的解法,加两个变量,一个记录当前层还需遍历的节点数,另一个记录下一层的节点数。
import java.util.ArrayList; import java.util.ArrayDeque; /** public class TreeNode { int val = 0; TreeNode left = null; TreeNode right = null; public TreeNode(int val) { this.val = val; } } */ public class Solution { public ArrayList<Integer> PrintFromTopToBottom(TreeNode root) { ArrayList<Integer> ans = new ArrayList<>(); if(root==null) return ans; ArrayDeque<TreeNode> queue = new ArrayDeque<>(); queue.add(root); int thisLevelNodes = 1; int nextLevelNodes = 0; while(!queue.isEmpty()){ TreeNode p = queue.remove(); ans.add(p.val); thisLevelNodes--; if(p.left!=null) {queue.add(p.left);nextLevelNodes++;} if(p.right!=null) {queue.add(p.right);nextLevelNodes++;} if(thisLevelNodes==0){ thisLevelNodes=nextLevelNodes; nextLevelNodes=0; } //换行打印操作 } return ans; } }
32c:之字形打印,分析一下打印过程可知,进“队”的顺序变为先入后出了,所以应该改用Stack。
另外利用上面的分行方法,设置boolean isOdd来判断是奇数行还是偶数行从而判断应该先进栈右孩子还是左孩子。
import java.util.ArrayList; import java.util.Stack; /** public class TreeNode { int val = 0; TreeNode left = null; TreeNode right = null; public TreeNode(int val) { this.val = val; } } */ public class Solution { public ArrayList<Integer> PrintFromTopToBottom(TreeNode root) { ArrayList<Integer> ans = new ArrayList<>(); if(root==null) return ans; Stack<TreeNode> stack1 = new Stack<>(); //for odd rows Stack<TreeNode> stack2 = new Stack<>(); //for even rows stack1.push(root); boolean isOdd = true; int thisLevelNodes=1; int nextLevelNodes=0; while(!stack1.empty()||!stack2.empty()){ if(isOdd){ TreeNode p = stack1.pop(); ans.add(p.val);thisLevelNodes--; if(p.left!=null){stack2.push(p.left);nextLevelNodes++;} if(p.right!=null){stack2.push(p.right);nextLevelNodes++;} }else{ TreeNode p = stack2.pop(); ans.add(p.val);thisLevelNodes--; if(p.right!=null){stack1.push(p.right);nextLevelNodes++;} if(p.left!=null){stack1.push(p.left);nextLevelNodes++;} } if(thisLevelNodes==0){ thisLevelNodes=nextLevelNodes; nextLevelNodes=0; isOdd = !isOdd; } } return ans; } }

浙公网安备 33010602011771号