题目描述
请实现两个函数,分别用来序列化和反序列化二叉树
思路
首先考虑将二叉树序列化,可以使用前序、中序、后序或者层次遍历的方式。
在做这道题之前,我考虑到的是,至少需要两个遍历序列才能恢复出一颗二叉树。
实则不然,如果要求输出的不是标准的前、中、后序遍历序列,我们完全可以对叶子节点进行标记。比如,叶子节点的左右子结点的值可以标记为"#",如此一来,我们也可以通过叶子节点来分割左右子树的序列。
我这道题选择使用前序遍历:
序列化的过程,实则是一个递归过程,同前序遍历的产生一致。唯一不同的点在于,将叶子节点的子结点(时则不存在)以"#“的形式存储在生成的序列里,每个节点的值都使用”,"分隔开。
注意:递归结束的条件就是子结点为null。
反序列化的过程,理所应当也是使用递归比较方便(但这不意味着迭代无法解决,只是太麻烦)。每次从序列中取出第一个结点作为根结点,然后将左子树指向对其余序列的反序列化,左子树反序列化(层层递归的过程)全都完成后,开始右子树的反序列化,最终得到一棵二叉树。
注意:递归结束的条件是遇到"#"或者字符串操作完毕。
题解
/*
public class TreeNode {
int val = 0;
TreeNode left = null;
TreeNode right = null;
public TreeNode(int val) {
this.val = val;
}
}
*/
public class Solution {
public String[] strs;
public int index=-1;
String Serialize(TreeNode root) {
StringBuffer sb = new StringBuffer();
if(root==null){
sb.append("#,");
return sb.toString();
}
sb.append(root.val+",");
sb.append(Serialize(root.left));
sb.append(Serialize(root.right));
return sb.toString();
}
TreeNode Deserialize(String str) {
if(strs == null){
strs = str.split(",");
}
index++;
if(index>=strs.length||strs[index].equals("#"))
return null;
else{
TreeNode root = new TreeNode(new Integer(strs[index]));
root.left = Deserialize(str);
root.right = Deserialize(str);
return root;
}
}
}