剑指offer题解13
56 对称的二叉树
题目描述
请实现一个函数,用来判断一颗二叉树是不是对称的。注意,如果一个二叉树同此二叉树的镜像是同样的,定义其为对称的。
分析:右的右与左的左互为镜像,右的左与左的右互为镜像
public class Solution {
boolean isSymmetrical(TreeNode pRoot)
{
if(pRoot==null){
return true;
}
return help(pRoot.left,pRoot.right);
}
private boolean help(TreeNode left,TreeNode right){
if(left==null&&right==null){
return true;
}
if((left==null&&right!=null)||(left!=null&&right==null)||(left.val!=right.val)){
return false;
}
return help(left.left,right.right)&&help(left.right,right.left);
}
}
57 按之字形顺序打印二叉树
题目描述
请实现一个函数按照之字形打印二叉树,即第一行按照从左到右的顺序打印,第二层按照从右至左的顺序打印,第三行按照从左到右的顺序打印,其他行以此类推。
分析:层次遍历即可,根据从左或者从右扫描选择插入的方式:头插,尾插
public class Solution {
ArrayList<ArrayList<Integer> > res=new ArrayList<>();
public ArrayList<ArrayList<Integer> > Print(TreeNode pRoot) {
if(pRoot==null){
return res;
}
ArrayList<TreeNode> queue=new ArrayList<>();
queue.add(pRoot);
boolean isLeft=true;
while(queue.size()!=0){
int size=queue.size();
ArrayList<Integer> temp=new ArrayList<>();
for(int i=0;i<size;i++){
//模拟队列
TreeNode curr=queue.get(0);
queue.remove(0);
//添加到queue中,层次遍历
if(curr.left!=null){
queue.add(curr.left);
}
if(curr.right!=null){
queue.add(curr.right);
}
//从左就插到尾部,从右就插到头部
if(isLeft){
temp.add(curr.val);
}else{
temp.add(0,curr.val);
}
}
res.add(temp);
isLeft=!isLeft;
}
return res;
}
}
58 层次遍历二叉树
题目描述
从上到下按层打印二叉树,同一层结点从左至右输出。每一层输出一行。
分析:使用队列
import java.util.ArrayList;
/*
public class TreeNode {
int val = 0;
TreeNode left = null;
TreeNode right = null;
public TreeNode(int val) {
this.val = val;
}
}
*/
public class Solution {
ArrayList<ArrayList<Integer> > res=new ArrayList<>();
ArrayList<ArrayList<Integer> > Print(TreeNode pRoot) {
if(pRoot==null){
return res;
}
ArrayList<TreeNode> queue=new ArrayList<>();
queue.add(pRoot);
while(queue.size()!=0){
int size=queue.size();
ArrayList<Integer> temp=new ArrayList<>();
for(int i=0;i<size;i++){
//模拟队列
TreeNode curr=queue.get(0);
queue.remove(0);
//添加到queue中,层次遍历
if(curr.left!=null){
queue.add(curr.left);
}
if(curr.right!=null){
queue.add(curr.right);
}
temp.add(curr.val);
}
res.add(temp);
}
return res;
}
}
59 序列化和反序列化
题目描述
请实现两个函数,分别用来序列化和反序列化二叉树
分析:我的第一想法是存储两个数组,表示先序遍历和中序遍历,然后反序列化的时候再根据两个序列构造一棵树;但是后来想没这么麻烦,直接使用先序遍历标记null即可
/*
public class TreeNode {
int val = 0;
TreeNode left = null;
TreeNode right = null;
public TreeNode(int val) {
this.val = val;
}
}
*/
public class Solution {
private int index=-1;
String Serialize(TreeNode root) {
if(root==null){
return "";
}
StringBuilder sb=new StringBuilder();
mySerialize(root,sb);
return sb.toString();
}
TreeNode Deserialize(String str) {
if(str.length()==0){
return null;
}
String[] strs=str.split(",");
return myDeserialize(strs);
}
private void mySerialize(TreeNode root,StringBuilder sb){
if(root==null){
sb.append("#,");
return ;
}
int val=root.val;
sb.append(String.valueOf(val)).append(",");
mySerialize(root.left,sb);
mySerialize(root.right,sb);
}
private TreeNode myDeserialize(String[] strs){
if(index==strs.length){
return null;
}
index++;
TreeNode tree=null;
String curr=strs[index];
if(!curr.equals("#")){
tree=new TreeNode(Integer.valueOf(curr));
tree.left=myDeserialize(strs);
tree.right=myDeserialize(strs);
}
return tree;
}
}