Skip to content

Commit 280deef

Browse files
1028 Recover a Tree From Preorder Traversal.py
1 parent 2801f65 commit 280deef

File tree

1 file changed

+143
-0
lines changed

1 file changed

+143
-0
lines changed
Lines changed: 143 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,143 @@
1+
#!/usr/bin/python3
2+
"""
3+
We run a preorder depth first search on the root of a binary tree.
4+
5+
At each node in this traversal, we output D dashes (where D is the depth of this
6+
node), then we output the value of this node. (If the depth of a node is D, the
7+
depth of its immediate child is D+1. The depth of the root node is 0.)
8+
9+
If a node has only one child, that child is guaranteed to be the left child.
10+
11+
Given the output S of this traversal, recover the tree and return its root.
12+
13+
14+
Example 1:
15+
Input: "1-2--3--4-5--6--7"
16+
Output: [1,2,5,3,4,6,7]
17+
18+
Example 2:
19+
Input: "1-2--3---4-5--6---7"
20+
Output: [1,2,5,3,null,6,null,4,null,7]
21+
22+
23+
Example 3:
24+
Input: "1-401--349---90--88"
25+
Output: [1,401,null,349,88,90]
26+
27+
28+
Note:
29+
The number of nodes in the original tree is between 1 and 1000.
30+
Each node will have a value between 1 and 10^9.
31+
"""
32+
33+
34+
# Definition for a binary tree node.
35+
class TreeNode:
36+
def __init__(self, x):
37+
self.val = x
38+
self.left = None
39+
self.right = None
40+
41+
from collections import OrderedDict
42+
43+
44+
class Solution:
45+
def recoverFromPreorder(self, S: str) -> TreeNode:
46+
"""
47+
map: node -> depth
48+
stack of pi (incompleted)
49+
"""
50+
depth = 0
51+
# parse
52+
n = len(S)
53+
i = 0
54+
root = None
55+
stk = []
56+
while i < n:
57+
if S[i] == "-":
58+
depth += 1
59+
i += 1
60+
else:
61+
j = i
62+
while j < n and S[j] != "-":
63+
j += 1
64+
65+
val = int(S[i:j])
66+
67+
# construct
68+
cur = TreeNode(val)
69+
if depth == 0:
70+
root = cur
71+
stk = [(depth, root)]
72+
else:
73+
assert stk
74+
while stk[-1][0] != depth - 1:
75+
stk.pop()
76+
77+
_, pi = stk[-1]
78+
if not pi.left:
79+
pi.left = cur
80+
elif not pi.right:
81+
pi.right = cur
82+
stk.pop()
83+
else:
84+
raise
85+
stk.append((depth, cur))
86+
87+
depth = 0
88+
i = j
89+
90+
return root
91+
92+
def recoverFromPreorder_error(self, S: str) -> TreeNode:
93+
"""
94+
map: node -> depth
95+
stack of pi (incompleted)
96+
"""
97+
depth = 0
98+
depths = OrderedDict()
99+
# parse
100+
n = len(S)
101+
i = 0
102+
while i < n:
103+
if S[i] == "-":
104+
depth += 1
105+
i += 1
106+
else:
107+
j = i
108+
while j < n and S[j] != "-":
109+
j += 1
110+
111+
val = int(S[i:j])
112+
depths[val] = depth
113+
depth = 0
114+
i = j
115+
116+
# construct
117+
stk = []
118+
root = None
119+
for k, v in depths.items():
120+
cur = TreeNode(k)
121+
if v == 0:
122+
root = cur
123+
stk = [root]
124+
else:
125+
assert stk
126+
while depths[stk[-1].val] != v - 1:
127+
stk.pop()
128+
129+
if not stk[-1].left:
130+
stk[-1].left = cur
131+
elif not stk[-1].right:
132+
stk[-1].right = cur
133+
stk.pop()
134+
else:
135+
raise
136+
stk.append(cur)
137+
138+
return root
139+
140+
141+
if __name__ == "__main__":
142+
assert Solution().recoverFromPreorder("5-4--4")
143+
assert Solution().recoverFromPreorder("1-2--3--4-5--6--7")

0 commit comments

Comments
 (0)