331. Verify Preorder Serialization of a Binary Tree

One way to serialize a binary tree is to use pre-order traversal. When we encounter a non-null node, we record the node's value. If it is a null node, we record using a sentinel value such as #.

     _9_
    /   \
   3     2
  / \   / \
 4   1  #  6
/ \ / \   / \
# # # #   # #

For example, the above binary tree can be serialized to the string "9,3,4,#,#,1,#,#,2,#,6,#,#", where # represents a null node.

Given a string of comma separated values, verify whether it is a correct preorder traversal serialization of a binary tree. Find an algorithm without reconstructing the tree.
Each comma separated value in the string must be either an integer or a character '#' representing null pointer.
You may assume that the input format is always valid, for example it could never contain two consecutive commas such as "1,,3".

Solution1:Stack

思路:
using a stack, scan left to right
case 1: we see a number, just push it to the stack
case 2: we see #, check if the top of stack is also #
(1) if so, pop #, recursively pop "c#" * n, and push a #
(2) if not, push this # to stack

331. Verify Preorder Serialization of a Binary Tree_第1张图片
屏幕快照 2017-09-19 下午6.06.42.png

实现1_a:原始思路
实现1_b:代码整理后
Time Complexity: O(N) Space Complexity: O(N)

Solution2:In/out degree

思路:

  1. For any graph sum of total indegree should be equal to total outdegree
  2. preorder 遍历时,整体累积的diff = outdegree - indegree,不会小于0。
331. Verify Preorder Serialization of a Binary Tree_第2张图片
屏幕快照 2017-09-19 下午10.04.35.png

Solution1_a Code:

public class Solution {
    public boolean isValidSerialization(String preorder) {
        // using a stack, scan left to right
        // case 1: we see a number, just push it to the stack
        
        // case 2: we see #, check if the top of stack is also #
        // if so, pop #, recursively pop "c#" * n, and push a #
        // if not, push this # to stack
        
        // in the end, check if stack size is 1, and stack top is #
        if (preorder == null) {
            return false;
        }
        
        ArrayDeque st = new ArrayDeque<>();
        String[] strs = preorder.split(",");
        for (int i = 0; i < strs.length; i++) {
            String curr = strs[i];
            
            // meet a number
            if(!curr.equals("#")) {
                st.push(curr);
            }
            
            // double #: meet # && stack top is #
            // then RECURSIVELY backwards pop c#, finially push #
            else if(curr.equals("#") && !st.isEmpty() && st.peek().equals("#")) {
                while(curr.equals("#") && !st.isEmpty() && st.peek().equals("#")) {
                    st.pop(); // pop #
                    if (st.isEmpty()) return false; // check
                    st.pop(); // pop number
                }
                st.push("#");
            }
            
            // meet # && stack top is not #
            else { 
                st.push(curr);
            }
        }
        
        return st.size() == 1 && st.peek().equals("#");
    }
}

Solution1_b Code:

public class Solution {
    public boolean isValidSerialization(String preorder) {
        // using a stack, scan left to right
        // case 1: we see a number, just push it to the stack
        
        // case 2: we see #, check if the top of stack is also #
        // if so, pop #, recursively pop "c#" * n, and push a #
        // if not, push this # to stack
        
        // in the end, check if stack size is 1, and stack top is #
        if (preorder == null) {
            return false;
        }
        
        ArrayDeque st = new ArrayDeque<>();
        String[] strs = preorder.split(",");
        for (int i = 0; i < strs.length; i++) {
            String curr = strs[i];
            
            // double #: meet # && stack top is #
            // then RECURSIVELY backwards pop c#, finially push #
            while(curr.equals("#") && !st.isEmpty() && st.peek().equals("#")) {
                st.pop(); // pop #
                if (st.isEmpty()) return false; // check
                st.pop(); // pop number
            }
            
            // (1) #, with stack top #: push # after recursive pop
            // (2) or meet a number: push that number
            // (3) or meet && stack top is not #: push #
            // all same, we can just:
            st.push(curr);
            
        }
        
        return st.size() == 1 && st.peek().equals("#");
    }
}

Solution2 Code:

class Solution {
    public boolean isValidSerialization(String preorder) {
        String[] nodes = preorder.split(",");
        int diff = 1;
        for (String node: nodes) {
            diff--;
            if (diff < 0) return false;
            if (!node.equals("#")) diff += 2;
        }
        return diff == 0;
    }
}

你可能感兴趣的:(331. Verify Preorder Serialization of a Binary Tree)