297. Serialize and Deserialize Binary Tree

用String表示BinaryTree,然后在通过String还原刚才的BinaryTree.

其实我感觉LeetCode一直用的一层一层的表达方式就挺好的,通过BFS实现的。

这里如果是DFS的话,那么就pre/in/post选一种,应该都可以。

有2个需要记录,1个是每个NODE的值,1个是结构,结构可以通过#来标记NULL.

如果都只有一位数,直接一个STRING就能搞定,否则还得用别的符号区分NODE和NODE,随便找个就行,我傻不拉几的用.区分,然后split的时候又他妈写成split(".")。。

还原的时候先通过刚才订的符号分割,然后根据pre/in/post来加到有顺序的数据结构了就行了,stack或者queue根据需要。

public class Codec 
{

    // Encodes a tree to a single string.
    public String serialize(TreeNode root) 
    {
        if(root == null) return "#";
        StringBuilder sb = new StringBuilder();
        helper(root,sb);
        
        return sb.toString();
        
        
    }
    
    public void helper(TreeNode root,StringBuilder sb)
    {
        if(root == null)
        {
            sb.append("#.");
            return;
        }
        
        sb.append(root.val).append(".");;
        helper(root.left,sb);
        helper(root.right,sb);
        
    }

    // Decodes your encoded data to tree.
    public TreeNode deserialize(String data) 
    {

        String[] str = data.split("\.");
        Queue<String> q = new LinkedList<String>();
        for(String n: str) q.add(n);
        
    
        return awesome(q);
        
    }
    
    
    public TreeNode awesome(Queue<String> q)
    {
       String tempStr = q.poll();
       if(tempStr.equals("#")) return null;
       
       TreeNode root = new TreeNode(Integer.valueOf(tempStr));
       
       if(q.size() != 0) root.left = awesome(q);
       if(q.size() != 0) root.right = awesome(q);
       
        
        return root;
        
        
    }
}

leetcode见过2道还原binary tree的题,给你in-order pre-order post-order其中2个,让你还原。

这里也可以,选其中2个方式各遍历一次,弄成1个Sring。还原的时候String平均分两半,剩下就和那俩题一样。坏处是时间上比较麻烦,空间说不定能省= =

代码就不写了。



二刷。

这个题居然是二刷,完全没印象。。。

二刷的开始,decode用array做的,传index传乱了几次,后来换成Queue了。。

public class Codec {

    // Encodes a tree to a single string.
    public String serialize(TreeNode root) {
        if (root == null) return "X#";
        StringBuilder sb = new StringBuilder();
        encode(root, sb);
        return sb.toString();
    }
    
    public void encode(TreeNode root, StringBuilder sb) {
        
        if (root == null) {
            sb.append("X#");
        } else {
            sb.append(root.val).append("#");
            encode(root.left, sb);
            encode(root.right, sb);
        }
        
    }

    // Decodes your encoded data to tree.
    public TreeNode deserialize(String data) {
        Queue<String> q = new LinkedList<>();
        q.addAll(Arrays.asList(data.split("#")));
        return decode(q);
    }
    
    public TreeNode decode(Queue<String> q) {
        if(q.isEmpty()) return null;
        String s = q.poll();
        if (s.equals("X")) {
            return null;
        } else {
            TreeNode res = new TreeNode(Integer.valueOf(s));
            res.left = decode(q);
            res.right = decode(q);
            return res;
        }
        
        
    }
}

回头发现这个题居然做过,然后一刷也是用的Queue,唯一的进步是把

for(String s: str) q.offer(s);

写成了

q.addAll(Arrays.asList(str));

好好分析下这个题。
用的思想其实是通过添加特殊符号把整个树补完整,否则[1,2]2是左是右都没法确定,言外之意是没法确定结构。

DFS和BFS应该都可以。

感觉BFS的问题就是要分层= =...
按这个思路想了一下,得记录上一层,或者得知道下一层的位置,比较麻烦。又或者可以理解为,得有个queue来保留上一层。

试试。。

搞定= =按层encode,记得补全NULL。

decode的时候,用一个Queue来记录上一层,每次添加左边添加右边,NULL就不放到Queue里就行了。。

public class Codec {

    // Encodes a tree to a single string.
    public String serialize(TreeNode root) {
        if (root == null) return "X#";
        StringBuilder sb = new StringBuilder();
        TreeNode temp = null;
        Queue<TreeNode> q = new LinkedList<>();
        q.offer(root);
        while (!q.isEmpty()) {
            temp = q.poll();
            if (temp == null) {
                sb.append("X#");
            } else {
                sb.append(temp.val + "#");
                q.offer(temp.left);
                q.offer(temp.right);
            }
        }
        return sb.toString();
    }
    


    // Decodes your encoded data to tree.
    public TreeNode deserialize(String data) {
        if (data.equals("X#")) return null;
        
        String[] s = data.split("#");
        TreeNode root = new TreeNode(Integer.valueOf(s[0]));
        Queue<TreeNode> q = new LinkedList<>();
        q.offer(root);
        TreeNode temp = null;
        for (int i = 1; i < s.length; ) {
            temp = q.poll();
            if (s[i].equals("X")) {
                temp.left = null;
            } else {
                temp.left = new TreeNode(Integer.valueOf(s[i]));
                q.offer(temp.left);
            }
            i ++;
            if (s[i].equals("X")) {
                temp.right = null;
            } else {
                temp.right = new TreeNode(Integer.valueOf(s[i]));
                q.offer(temp.right);
            }
            i ++;
        }
        return root;
        
    }
    

}
Operation Time Space
DFS Encode O(N) O(lgN) + O(N)
DFS Decode O(N) O(lgN) + O(N)
BFS Eecode O(N) O(N) + O(N)
BFS Decode O(N) O(N) + O(N)

什么乱七八糟的。。。破表格。反正基本就是O(N)

有的时候多个stack的内存空间,有时候多个Queue,不复杂。。

原文地址:https://www.cnblogs.com/reboot329/p/5892233.html