剑指offer——按之字形打印二叉树
1、题目描述
请实现一个函数按照之字形打印二叉树,即第一行按照从左到右的顺序打印,第二层按照从右至左的顺序打印,第三行按照从左到右的顺序打印,其他行以此类推。
2、我的思路
隔行,奇数行存在队列里,偶数行存在栈中。
错误解法:
import java.util.ArrayList;
import java.util.Stack;
import java.util.Queue;
import java.util.LinkedList;
/*
public class TreeNode {
int val = 0;
TreeNode left = null;
TreeNode right = null;
public TreeNode(int val) {
this.val = val;
}
}
*/
public class Solution {
public ArrayList<ArrayList<Integer> > Print(TreeNode pRoot) {
ArrayList<ArrayList<Integer>> arrays=new ArrayList<ArrayList<Integer>>();
Stack<TreeNode> stack=new Stack<TreeNode>();
Queue<TreeNode> queue=new LinkedList<TreeNode>();
queue.offer(pRoot);
while(!queue.isEmpty() || !stack.isEmpty()){
if(!queue.isEmpty()){
ArrayList<Integer> array1=new ArrayList<Integer>();
while(!queue.isEmpty()){
if(queue.peek().left!=null){
stack.push(queue.peek().left);
}
if(queue.peek().right!=null){
stack.push(queue.peek().right);
}
array1.add(queue.poll().val);
}
arrays.add(array1);
}else{
ArrayList<Integer> array2=new ArrayList<Integer>();
while(!stack.isEmpty()){
if(stack.peek().left!=null){
queue.offer(stack.peek().left);
}
if(stack.peek().right!=null){
queue.offer(stack.peek().right);
}
array2.add(stack.pop().val);
}
arrays.add(array2);
}
}
return arrays;
}
}
不通过
您的代码已保存
答案错误:您提交的程序没有通过所有的测试用例
case通过率为0.00%
测试用例:
{8,6,10,5,7,9,11}
对应输出应该为:
[[8],[10,6],[5,7,9,11]]
你的输出为:
[[8],[10,6],[9,11,5,7]]
理由:
栈中,先进后出,因此第一次读取栈中元素,并将下一行存入队列中时,所存下一行顺序并不是从左到右依次存的。
改正解法:
增加一个数组,保存TreeNode节点,并从后向前读取该数组,得到从左到右的正确顺序。
import java.util.ArrayList;
import java.util.Stack;
import java.util.Queue;
import java.util.LinkedList;
/*
public class TreeNode {
int val = 0;
TreeNode left = null;
TreeNode right = null;
public TreeNode(int val) {
this.val = val;
}
}
*/
public class Solution {
public ArrayList<ArrayList<Integer> > Print(TreeNode pRoot) {
ArrayList<ArrayList<Integer>> arrays=new ArrayList<ArrayList<Integer>>();
if(pRoot==null){
return arrays;
}//一定要注意该种情况,否则容易发生空指针异常。
Stack<TreeNode> stack=new Stack<TreeNode>();
Queue<TreeNode> queue=new LinkedList<TreeNode>();
queue.offer(pRoot);
while(!queue.isEmpty() || !stack.isEmpty()){
if(!queue.isEmpty()){
ArrayList<Integer> array1=new ArrayList<Integer>();
while(!queue.isEmpty()){
if(queue.peek().left!=null){
stack.push(queue.peek().left);
}
if(queue.peek().right!=null){
stack.push(queue.peek().right);
}
array1.add(queue.poll().val);
}
arrays.add(array1);
}else{
ArrayList<Integer> array2=new ArrayList<Integer>();
ArrayList<TreeNode> array3=new ArrayList<TreeNode>();
while(!stack.isEmpty()){
array2.add(stack.peek().val);
array3.add(stack.pop());
}
for(int i=array3.size()-1;i>=0;i--){
if(array3.get(i).left!=null){
queue.offer(array3.get(i).left);
}
if(array3.get(i).right!=null){
queue.offer(array3.get(i).right);
}
}
arrays.add(array2);
}
}
return arrays;
}
}
3、他人类似解法
利用两个栈,一个栈先左后右进栈,一个栈先右后左进栈。
import java.util.*;
/*
public class TreeNode {
int val = 0;
TreeNode left = null;
TreeNode right = null;
public TreeNode(int val) {
this.val = val;
}
}
*/
public class Solution {
public ArrayList<ArrayList<Integer> > Print(TreeNode pRoot) {
ArrayList<ArrayList<Integer>> aList=new ArrayList<ArrayList<Integer>>();
if(pRoot==null)
return aList;
Stack<TreeNode> s1=new Stack<TreeNode>();
s1.add(pRoot);
Stack<TreeNode> s2=new Stack<TreeNode>();
while(!s1.isEmpty()||!s2.isEmpty()){
if(!s1.isEmpty()){
ArrayList<Integer> aList2=new ArrayList<Integer>();
while(!s1.isEmpty()){
TreeNode p=s1.pop();
aList2.add(p.val);
if(p.left!=null)
s2.add(p.left);
if(p.right!=null)
s2.add(p.right);
}
aList.add(aList2);
}else {
ArrayList<Integer> aList2=new ArrayList<Integer>();
while(!s2.isEmpty()){
TreeNode p=s2.pop();
if(p.right!=null)
s1.add(p.right);
if(p.left!=null)
s1.add(p.left);
aList2.add(p.val);
}
aList.add(aList2);
}
}
return aList;
}
}
参考资料:
Java编程思想—11.11—队列(Queue)