11 void _tree_init(Tree
* tree
, size_t dataSize
)
14 tree
->dataSize
= dataSize
;
18 Tree
* _tree_new(size_t dataSize
)
20 Tree
* tree
= (Tree
*) safe_malloc(sizeof (Tree
));
21 _tree_init(tree
, dataSize
);
25 Tree
* tree_copy(Tree
* tree
)
27 Tree
* treeCopy
= _tree_new(tree
->dataSize
);
28 if (tree
->root
== NULL
)
30 _tree_set_root(treeCopy
, tree
->root
->data
);
32 // Now parallel run on both trees (manual breadth-first walk)
33 TreeNode
* treeNode
= tree
->root
;
34 TreeNode
* treeNodeCopy
= treeCopy
->root
;
35 while (treeNode
!= NULL
)
37 // process current children
38 TreeNode
* child
= treeNode
->firstChild
;
41 _tree_add_child(treeCopy
, treeNodeCopy
, child
->data
);
45 // try to go to next sibling (NOTE: already added as child of parent)
46 if (treeNode
->next
!= NULL
)
48 treeNode
= treeNode
->next
;
49 treeNodeCopy
= treeNodeCopy
->next
;
53 // try to go to next "cousin" on same level
54 if (treeNode
->parent
!= NULL
&& treeNode
->parent
->next
!= NULL
)
56 TreeNode
* treeNodeParent
= treeNode
->parent
->next
;
57 TreeNode
* treeNodeParentCopy
= treeNodeCopy
->parent
->next
;
58 while (treeNodeParent
!= NULL
&& tree_is_leaf(treeNodeParent
))
60 treeNodeParent
= treeNodeParent
->next
;
61 treeNodeParentCopy
= treeNodeParentCopy
->next
;
63 if (treeNodeParent
!= NULL
)
65 treeNode
= treeNodeParent
->firstChild
;
66 treeNodeCopy
= treeNodeParentCopy
->firstChild
;
71 // try to go to next level, and move treeNodeCopy accordingly
72 while (treeNode
->prev
!= NULL
)
74 treeNode
= treeNode
->prev
;
75 treeNodeCopy
= treeNodeCopy
->prev
;
77 while (treeNode
!= NULL
&& tree_is_leaf(treeNode
))
79 treeNode
= treeNode
->next
;
80 treeNodeCopy
= treeNodeCopy
->next
;
84 treeNode
= treeNode
->firstChild
;
85 treeNodeCopy
= treeNodeCopy
->firstChild
;
91 Bool
tree_empty(Tree
* tree
)
93 return (tree
->root
== NULL
);
96 UInt
tree_size(Tree
* tree
)
101 UInt
_tree_height_rekursiv(TreeNode
* treeNode
)
103 if (tree_is_leaf(treeNode
))
105 TreeNode
* child
= treeNode
->firstChild
;
106 UInt maxHeightChild
= 0;
107 while (child
!= NULL
)
109 UInt heightChild
= _tree_height_rekursiv(child
);
110 if (heightChild
> maxHeightChild
)
111 maxHeightChild
= heightChild
;
114 return 1 + maxHeightChild
;
117 UInt
tree_height(Tree
* tree
)
119 if (tree_empty(tree
))
121 return _tree_height_rekursiv(tree
->root
);
124 Bool
tree_is_leaf(TreeNode
* treeNode
)
126 return (treeNode
->firstChild
== NULL
);
129 void _tree_set_root(Tree
* tree
, void* data
)
131 tree
->root
= (TreeNode
*) safe_malloc(sizeof (TreeNode
));
132 tree
->root
->data
= safe_malloc(tree
->dataSize
);
133 memcpy(tree
->root
->data
, data
, tree
->dataSize
);
134 tree
->root
->parent
= NULL
;
135 tree
->root
->firstChild
= NULL
;
136 tree
->root
->lastChild
= NULL
;
137 tree
->root
->prev
= NULL
;
138 tree
->root
->next
= NULL
;
142 void* _tree_get(TreeNode
* treeNode
)
144 return treeNode
->data
;
147 void _tree_set(Tree
* tree
, TreeNode
* treeNode
, void* data
)
149 memcpy(treeNode
->data
, data
, tree
->dataSize
);
152 void _tree_add_child(Tree
* tree
, TreeNode
* treeNode
, void* data
)
154 TreeNode
* newChildNode
= (TreeNode
*) safe_malloc(sizeof (TreeNode
));
155 newChildNode
->data
= safe_malloc(tree
->dataSize
);
156 memcpy(newChildNode
->data
, data
, tree
->dataSize
);
157 newChildNode
->next
= NULL
;
158 if (treeNode
->lastChild
!= NULL
)
159 treeNode
->lastChild
->next
= newChildNode
;
160 newChildNode
->prev
= treeNode
->lastChild
;
161 treeNode
->lastChild
= newChildNode
;
162 if (treeNode
->firstChild
== NULL
)
163 treeNode
->firstChild
= newChildNode
;
164 newChildNode
->parent
= treeNode
;
165 newChildNode
->firstChild
= NULL
;
166 newChildNode
->lastChild
= NULL
;
170 void _tree_add_sibling(Tree
* tree
, TreeNode
* treeNode
, void* data
)
172 TreeNode
* newSiblingNode
= (TreeNode
*) safe_malloc(sizeof (TreeNode
));
173 newSiblingNode
->data
= safe_malloc(tree
->dataSize
);
174 memcpy(newSiblingNode
->data
, data
, tree
->dataSize
);
175 newSiblingNode
->next
= treeNode
->next
;
176 if (treeNode
->next
!= NULL
)
177 treeNode
->next
->prev
= newSiblingNode
;
178 newSiblingNode
->prev
= treeNode
;
179 treeNode
->next
= newSiblingNode
;
180 newSiblingNode
->parent
= treeNode
->parent
;
181 newSiblingNode
->firstChild
= NULL
;
182 newSiblingNode
->lastChild
= NULL
;
186 void _tree_remove_rekursiv(Tree
* tree
, TreeNode
* treeNode
)
188 TreeNode
* child
= treeNode
->firstChild
;
189 while (child
!= NULL
)
191 TreeNode
* nextChild
= child
->next
;
192 _tree_remove_rekursiv(tree
, child
);
195 safe_free(treeNode
->data
);
200 void tree_remove(Tree
* tree
, TreeNode
* treeNode
)
202 if (treeNode
->parent
!= NULL
)
204 if (treeNode
->prev
== NULL
)
205 treeNode
->parent
->firstChild
= treeNode
->next
;
206 if (treeNode
->next
== NULL
)
207 treeNode
->parent
->lastChild
= treeNode
->prev
;
209 if (treeNode
->next
!= NULL
)
210 treeNode
->next
->prev
= treeNode
->prev
;
211 if (treeNode
->prev
!= NULL
)
212 treeNode
->prev
->next
= treeNode
->next
;
213 _tree_remove_rekursiv(tree
, treeNode
);
216 void tree_rm_childs(Tree
* tree
, TreeNode
* treeNode
)
218 TreeNode
* child
= treeNode
->firstChild
;
219 while (child
!= NULL
)
221 TreeNode
* nextChild
= child
->next
;
222 _tree_remove_rekursiv(tree
, child
);
225 treeNode
->firstChild
= NULL
;
226 treeNode
->lastChild
= NULL
;
229 void tree_clear(Tree
* tree
)
231 if (tree
->root
!= NULL
)
232 _tree_remove_rekursiv(tree
, tree
->root
);
233 _tree_init(tree
, tree
->dataSize
);
236 void tree_destroy(Tree
* tree
)
238 if (tree
->root
!= NULL
)
247 TreeIterator
* tree_get_iterator(Tree
* tree
, TreeIteratorMode mode
)
249 TreeIterator
* treeI
= (TreeIterator
*) safe_malloc(sizeof (TreeIterator
));
256 void treeI_reset(TreeIterator
* treeI
)
258 treeI
->current
= treeI
->tree
->root
;
261 Bool
treeI_has_data(TreeIterator
* treeI
)
263 return (treeI
->current
!= NULL
);
266 TreeNode
* treeI_get_raw(TreeIterator
* treeI
)
268 return treeI
->current
;
271 void treeI_move_next(TreeIterator
* treeI
)
273 TreeIteratorMode mode
= treeI
->mode
;
277 if (!tree_is_leaf(treeI
->current
))
279 // easy case: just descend deeper in the tree
280 treeI
->current
= treeI
->current
->firstChild
;
283 // leaf: while no next sibling is available, move up
284 while (treeI
->current
!= NULL
&& treeI
->current
->next
== NULL
)
285 treeI
->current
= treeI
->current
->parent
;
286 if (treeI
->current
!= NULL
)
287 // run goes on from next sibling
288 treeI
->current
= treeI
->current
->next
;
291 if (treeI
->current
->next
!= NULL
)
293 // easy case : just move to the next sibling
294 treeI
->current
= treeI
->current
->next
;
297 // try to go to next "cousin" on same level
298 if (treeI
->current
->parent
!= NULL
&& treeI
->current
->parent
->next
!= NULL
)
300 TreeNode
* treeNodeParent
= treeI
->current
->parent
->next
;
301 while (treeNodeParent
!= NULL
&& tree_is_leaf(treeNodeParent
))
302 treeNodeParent
= treeNodeParent
->next
;
303 if (treeNodeParent
!= NULL
)
305 treeI
->current
= treeNodeParent
->firstChild
;
309 // try to go to next level
310 while (treeI
->current
->prev
!= NULL
)
311 treeI
->current
= treeI
->current
->prev
;
312 while (treeI
->current
!= NULL
&& tree_is_leaf(treeI
->current
))
313 treeI
->current
= treeI
->current
->next
;
314 if (treeI
->current
!= NULL
)
315 treeI
->current
= treeI
->current
->firstChild
;
320 void treeI_destroy(TreeIterator
* treeI
)