Skip to content

Commit 4d1fcbb

Browse files
committed
LeetCode 589. N-ary Tree Preorder Traversal
1 parent da33e97 commit 4d1fcbb

File tree

2 files changed

+87
-0
lines changed

2 files changed

+87
-0
lines changed

README.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ Proposed solutions to some LeetCode problems. The first column links to the prob
5050
| [509. Fibonacci Number][lc509] | Easy | [python](leetcode/fibonacci-number.py) |
5151
| [583. Delete Operation for Two Strings][lc583] | Medium | [python](leetcode/delete-operation-for-two-strings.py) |
5252
| [587. Erect the Fence][lc587] | Hard | [python](leetcode/erect-the-fence.py) |
53+
| [589. N-ary Tree Preorder Traversal][lc589] | Easy | [python](leetcode/n-ary-tree-preorder-traversal.py) |
5354
| [596. Classes More Than 5 Students][lc596] | Easy | [mysql](leetcode/classes_more_than_5_students.sql) |
5455
| [599. Minimum Index Sum of Two Lists][lc599] | Easy | [python](leetcode/minimum-index-sum-of-two-lists.py) |
5556
| [630. Course Schedule III][lc630] | Hard | [python](leetcode/course-schedule-iii.py) |
@@ -134,6 +135,7 @@ First column is the problem difficulty, in descending order, second links to the
134135
[lc509]: https://leetcode.com/problems/fibonacci-number/
135136
[lc583]: https://leetcode.com/problems/delete-operation-for-two-strings/
136137
[lc587]: https://leetcode.com/problems/erect-the-fence/
138+
[lc589]: https://leetcode.com/problems/n-ary-tree-preorder-traversal/
137139
[lc596]: https://leetcode.com/problems/classes-more-than-5-students/
138140
[lc599]: https://leetcode.com/problems/minimum-index-sum-of-two-lists/
139141
[lc630]: https://leetcode.com/problems/course-schedule-iii/
Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
# https://leetcode.com/problems/n-ary-tree-preorder-traversal/
2+
3+
import timeit
4+
from typing import List
5+
6+
7+
class Node:
8+
def __init__(self, val=None, children=None):
9+
self.val = val
10+
self.children = children
11+
12+
13+
# Runtime: 85 ms, faster than 38.18% of Python3 online submissions for N-ary Tree Preorder Traversal.
14+
# Memory Usage: 16.3 MB, less than 48.82 % of Python3 online submissions for N-ary Tree Preorder Traversal.
15+
class RecursiveDFS:
16+
def preorder(self, root: Node) -> List[int]:
17+
if not root:
18+
return []
19+
values = []
20+
21+
def dfs(node: Node):
22+
values.append(node.val)
23+
if node.children:
24+
for child_node in node.children:
25+
dfs(child_node)
26+
dfs(root)
27+
return values
28+
29+
30+
# Runtime: 88 ms, faster than 33.42% of Python3 online submissions for N-ary Tree Preorder Traversal.
31+
# Memory Usage: 16 MB, less than 80.88 % of Python3 online submissions for N-ary Tree Preorder Traversal.
32+
class IterativeDFS:
33+
def preorder(self, root: Node) -> List[int]:
34+
if not root:
35+
return []
36+
values = []
37+
stack = [root]
38+
while stack:
39+
node = stack.pop()
40+
# Visit the node we just popped
41+
values.append(node.val)
42+
# In python we need to check if the children [] is none before the for loop
43+
if node.children:
44+
# Reverse-push the children in the stack for pre-order
45+
for child_node in reversed(node.children):
46+
stack.append(child_node)
47+
return values
48+
49+
50+
class SelfRecursive:
51+
def preorder(self, root: 'Node') -> List[int]:
52+
if not root:
53+
return []
54+
result = [root.val]
55+
for node in root.children:
56+
result.extend(self.preorder(node))
57+
return result
58+
59+
60+
def test():
61+
executors = [RecursiveDFS, IterativeDFS, SelfRecursive]
62+
node6 = Node(val=6, children=[])
63+
node5 = Node(val=5, children=[])
64+
node4 = Node(val=4, children=[])
65+
node3 = Node(val=3, children=[node5, node6])
66+
node2 = Node(val=2, children=[])
67+
node1 = Node(val=1, children=[node3, node2, node4])
68+
tests = [
69+
[node1, [1, 3, 5, 6, 2, 4]],
70+
]
71+
for executor in executors:
72+
start = timeit.default_timer()
73+
for _ in range(int(float('1'))):
74+
for t in tests:
75+
sol = executor()
76+
result = sol.preorder(t[0])
77+
expected = t[1]
78+
assert result == expected, f'{result} != {expected}'
79+
stop = timeit.default_timer()
80+
used = str(round(stop - start, 5))
81+
res = "{0:20}{1:10}{2:10}".format(executor.__name__, used, "seconds")
82+
print(f"\033[92m» {res}\033[0m")
83+
84+
85+
test()

0 commit comments

Comments
 (0)