|
4 | 4 |
|
5 | 5 | #define BST_MAX_LEVEL 800 |
6 | 6 |
|
7 | | -#define container_of(ptr, type, member) \ |
8 | | - ((type *)((char *)(ptr) - (size_t)&(((type *)0)->member))) |
9 | | - |
10 | | -#define list_entry(ptr, type, member) \ |
11 | | - container_of(ptr, type, member) |
12 | | - |
13 | | -#define list_first_entry(ptr, type, field) list_entry((ptr)->next, type, field) |
14 | | -#define list_last_entry(ptr, type, field) list_entry((ptr)->prev, type, field) |
15 | | - |
16 | | -#define list_for_each(p, head) \ |
17 | | - for (p = (head)->next; p != (head); p = p->next) |
18 | | - |
19 | | -#define list_for_each_safe(p, n, head) \ |
20 | | - for (p = (head)->next, n = p->next; p != (head); p = n, n = p->next) |
21 | | - |
22 | 7 | struct TreeNode { |
23 | 8 | int val; |
24 | 9 | struct TreeNode *left; |
25 | 10 | struct TreeNode *right; |
26 | 11 | }; |
27 | 12 |
|
28 | | -struct list_head { |
29 | | - struct list_head *next, *prev; |
30 | | -}; |
31 | | - |
32 | | -static inline void INIT_LIST_HEAD(struct list_head *list) |
33 | | -{ |
34 | | - list->next = list->prev = list; |
35 | | -} |
36 | | - |
37 | | -static inline int list_empty(const struct list_head *head) |
38 | | -{ |
39 | | - return (head->next == head); |
40 | | -} |
41 | | - |
42 | | -static inline void __list_add(struct list_head *new, struct list_head *prev, struct list_head *next) |
43 | | -{ |
44 | | - next->prev = new; |
45 | | - new->next = next; |
46 | | - new->prev = prev; |
47 | | - prev->next = new; |
48 | | -} |
49 | | - |
50 | | -static inline void list_add(struct list_head *_new, struct list_head *head) |
51 | | -{ |
52 | | - __list_add(_new, head, head->next); |
53 | | -} |
54 | | - |
55 | | -static inline void list_add_tail(struct list_head *_new, struct list_head *head) |
56 | | -{ |
57 | | - __list_add(_new, head->prev, head); |
58 | | -} |
59 | | - |
60 | | -static inline void __list_del(struct list_head *entry) |
| 13 | +static void bfs(struct TreeNode *root, int **results, int *count, int *col_sizes, int *size, int level) |
61 | 14 | { |
62 | | - entry->next->prev = entry->prev; |
63 | | - entry->prev->next = entry->next; |
64 | | -} |
65 | | - |
66 | | -static inline void list_del(struct list_head *entry) |
67 | | -{ |
68 | | - __list_del(entry); |
69 | | - entry->next = entry->prev = NULL; |
70 | | -} |
71 | | - |
72 | | -struct bfs_node { |
73 | | - struct TreeNode *node; |
74 | | - struct list_head link; |
75 | | -}; |
76 | | - |
77 | | -static struct bfs_node *node_new(struct list_head *free_list, struct TreeNode *node) |
78 | | -{ |
79 | | - struct bfs_node *new; |
80 | | - if (list_empty(free_list)) { |
81 | | - new = malloc(sizeof(*new)); |
82 | | - } else { |
83 | | - new = list_first_entry(free_list, struct bfs_node, link); |
84 | | - list_del(&new->link); |
85 | | - } |
86 | | - new->node = node; |
87 | | - return new; |
88 | | -} |
89 | | - |
90 | | -static void queue(struct list_head *parents, struct list_head *children, |
91 | | - struct list_head *free_list, int **results, int *col_sizes, int level) |
92 | | -{ |
93 | | - struct list_head *p, *n; |
94 | | - list_for_each(p, parents) { |
95 | | - struct bfs_node *new; |
96 | | - struct bfs_node *parent = list_entry(p, struct bfs_node, link); |
97 | | - if (parent->node->left != NULL) { |
98 | | - new = node_new(free_list, parent->node->left); |
99 | | - list_add_tail(&new->link, children); |
100 | | - } |
101 | | - if (parent->node->right != NULL) { |
102 | | - new = node_new(free_list, parent->node->right); |
103 | | - list_add_tail(&new->link, children); |
104 | | - } |
105 | | - col_sizes[level]++; |
| 15 | + if (root == NULL) { |
| 16 | + return; |
106 | 17 | } |
107 | 18 |
|
108 | | - int i = 0; |
109 | | - results[level] = malloc(col_sizes[level] * sizeof(int)); |
110 | | - list_for_each_safe(p, n, parents) { |
111 | | - struct bfs_node *parent = list_entry(p, struct bfs_node, link); |
112 | | - results[level][i++] = parent->node->val; |
113 | | - list_del(p); |
114 | | - list_add(p, free_list); |
| 19 | + *count = level + 1 > *count ? level + 1 : *count; |
| 20 | + if (col_sizes[level] == 0) { |
| 21 | + *size = *size > 256 ? 256 : *size * 2; |
| 22 | + results[level] = malloc(*size * sizeof(int)); |
115 | 23 | } |
| 24 | + results[level][col_sizes[level]++] = root->val; |
| 25 | + bfs(root->left, results, count, col_sizes, size, level + 1); |
| 26 | + bfs(root->right, results, count, col_sizes, size, level + 1); |
116 | 27 | } |
117 | 28 |
|
118 | 29 | /** |
119 | 30 | ** Return an array of arrays of size *returnSize. |
120 | | - ** The sizes of the arrays are returned as *columnSizes array. |
| 31 | + ** The sizes of the arrays are returned as *returnColumnSizes array. |
121 | 32 | ** Note: Both returned array and *columnSizes array must be malloced, assume caller calls free(). |
122 | 33 | **/ |
123 | | -static int** levelOrder(struct TreeNode* root, int** columnSizes, int* returnSize) |
| 34 | +static int** levelOrder(struct TreeNode* root, int* returnSize, int** returnColumnSizes) |
124 | 35 | { |
125 | 36 | if (root == NULL) { |
126 | 37 | *returnSize = 0; |
127 | 38 | return NULL; |
128 | 39 | } |
129 | 40 |
|
130 | | - struct list_head free_list; |
131 | | - struct list_head q0; |
132 | | - struct list_head q1; |
133 | | - INIT_LIST_HEAD(&free_list); |
134 | | - INIT_LIST_HEAD(&q0); |
135 | | - INIT_LIST_HEAD(&q1); |
136 | | - |
| 41 | + int size = 1; |
| 42 | + *returnSize = 0; |
137 | 43 | int **results = malloc(BST_MAX_LEVEL * sizeof(int *)); |
138 | | - *columnSizes = malloc(BST_MAX_LEVEL * sizeof(int)); |
139 | | - memset(*columnSizes, 0, BST_MAX_LEVEL * sizeof(int)); |
140 | | - |
141 | | - int level = 0; |
142 | | - struct bfs_node *new = node_new(&free_list, root); |
143 | | - list_add_tail(&new->link, &q0); |
144 | | - |
145 | | - while (!list_empty(&q0) || !list_empty(&q1)) { |
146 | | - if (level & 0x1) { |
147 | | - queue(&q1, &q0, &free_list, results, *columnSizes, level); |
148 | | - } else { |
149 | | - queue(&q0, &q1, &free_list, results, *columnSizes, level); |
150 | | - } |
151 | | - level++; |
152 | | - } |
153 | | - |
154 | | - *returnSize = level; |
| 44 | + *returnColumnSizes = malloc(BST_MAX_LEVEL * sizeof(int)); |
| 45 | + memset(*returnColumnSizes, 0, BST_MAX_LEVEL * sizeof(int)); |
| 46 | + bfs(root, results, returnSize, *returnColumnSizes, &size, 0); |
155 | 47 | return results; |
156 | 48 | } |
157 | 49 |
|
@@ -186,7 +78,7 @@ int main(void) |
186 | 78 | node2[3].right = NULL; |
187 | 79 |
|
188 | 80 | int i, j, count = 0, *col_sizes; |
189 | | - int **lists = levelOrder(&root, &col_sizes, &count); |
| 81 | + int **lists = levelOrder(&root, &count, &col_sizes); |
190 | 82 | for (i = 0; i < count; i++) { |
191 | 83 | for (j = 0; j < col_sizes[i]; j++) { |
192 | 84 | printf("%d ", lists[i][j]); |
|
0 commit comments