11 typedef struct W_Node
{
12 struct W_Node
*parent
;
22 typedef struct W_TreeBag
{
25 W_Node
*nil
; /* sentinel */
32 static int getItemCount(WMBag
*self
);
33 static int appendBag(WMBag
*self
, WMBag
*bag
);
34 static int putInBag(WMBag
*self
, void *item
);
35 static int insertInBag(WMBag
*self
, int index
, void *item
);
36 static int removeFromBag(WMBag
*bag
, void *item
);
37 static int eraseFromBag(WMBag
*bag
, int index
);
38 static int deleteFromBag(WMBag
*bag
, int index
);
39 static void *getFromBag(WMBag
*bag
, int index
);
40 static int countInBag(WMBag
*bag
, void *item
);
41 static int firstInBag(WMBag
*bag
, void *item
);
42 static void *replaceInBag(WMBag
*bag
, int index
, void *item
);
43 static int sortBag(WMBag
*bag
, int (*comparer
)(const void*, const void*));
44 static void emptyBag(WMBag
*bag
);
45 static void freeBag(WMBag
*bag
);
46 static void mapBag(WMBag
*bag
, void (*function
)(void*, void*), void *data
);
47 static int findInBag(WMBag
*bag
, int (*match
)(void*));;
48 static void *first(WMBag
*bag
, WMBagIterator
*ptr
);
49 static void *last(WMBag
*bag
, WMBagIterator
*ptr
);
50 static void *next(WMBag
*bag
, WMBagIterator
*ptr
);
51 static void *previous(WMBag
*bag
, WMBagIterator
*ptr
);
52 static void *iteratorAtIndex(WMBag
*bag
, int index
, WMBagIterator
*ptr
);
53 static int indexForIterator(WMBag
*bag
, WMBagIterator ptr
);
56 static W_BagFunctions bagFunctions
= {
84 #define IS_LEFT(node) (node == node->parent->left)
85 #define IS_RIGHT(node) (node == node->parent->right)
89 static void leftRotate(W_TreeBag
*tree
, W_Node
*node
)
94 node
->right
= node2
->left
;
96 node2
->left
->parent
= node
;
98 node2
->parent
= node
->parent
;
100 if (node
->parent
== tree
->nil
) {
104 node
->parent
->left
= node2
;
106 node
->parent
->right
= node2
;
110 node
->parent
= node2
;
115 static void rightRotate(W_TreeBag
*tree
, W_Node
*node
)
120 node
->left
= node2
->right
;
122 node2
->right
->parent
= node
;
124 node2
->parent
= node
->parent
;
126 if (node
->parent
== tree
->nil
) {
130 node
->parent
->left
= node2
;
132 node
->parent
->right
= node2
;
136 node
->parent
= node2
;
141 static void treeInsert(W_TreeBag
*tree
, W_Node
*node
)
143 W_Node
*y
= tree
->nil
;
144 W_Node
*x
= tree
->root
;
146 while (x
!= tree
->nil
) {
148 if (node
->index
< x
->index
)
156 else if (node
->index
< y
->index
)
163 static void rbTreeInsert(W_TreeBag
*tree
, W_Node
*node
)
167 treeInsert(tree
, node
);
171 while (node
!= tree
->root
&& node
->parent
->color
== 'R') {
172 if (IS_LEFT(node
->parent
)) {
173 y
= node
->parent
->parent
->right
;
175 if (y
->color
== 'R') {
177 node
->parent
->color
= 'B';
179 node
->parent
->parent
->color
= 'R';
180 node
= node
->parent
->parent
;
183 if (IS_RIGHT(node
)) {
185 leftRotate(tree
, node
);
187 node
->parent
->color
= 'B';
188 node
->parent
->parent
->color
= 'R';
189 rightRotate(tree
, node
->parent
->parent
);
192 y
= node
->parent
->parent
->left
;
194 if (y
->color
== 'R') {
196 node
->parent
->color
= 'B';
198 node
->parent
->parent
->color
= 'R';
199 node
= node
->parent
->parent
;
204 rightRotate(tree
, node
);
206 node
->parent
->color
= 'B';
207 node
->parent
->parent
->color
= 'R';
208 leftRotate(tree
, node
->parent
->parent
);
212 tree
->root
->color
= 'B';
217 static void rbDeleteFixup(W_TreeBag
*tree
, W_Node
*node
)
221 while (node
!= tree
->root
&& node
->color
== 'B') {
223 w
= node
->parent
->right
;
224 if (w
->color
== 'R') {
226 node
->parent
->color
= 'R';
227 leftRotate(tree
, node
->parent
);
228 w
= node
->parent
->right
;
230 if (w
->left
->color
== 'B' && w
->right
->color
== 'B') {
234 if (w
->right
->color
== 'B') {
235 w
->left
->color
= 'B';
237 rightRotate(tree
, w
);
238 w
= node
->parent
->right
;
240 w
->color
= node
->parent
->color
;
241 node
->parent
->color
= 'B';
242 w
->right
->color
= 'B';
243 leftRotate(tree
, node
->parent
);
247 w
= node
->parent
->left
;
248 if (w
->color
== 'R') {
250 node
->parent
->color
= 'R';
251 leftRotate(tree
, node
->parent
);
252 w
= node
->parent
->left
;
254 if (w
->left
->color
== 'B' && w
->right
->color
== 'B') {
258 if (w
->left
->color
== 'B') {
259 w
->right
->color
= 'B';
261 rightRotate(tree
, w
);
262 w
= node
->parent
->left
;
264 w
->color
= node
->parent
->color
;
265 node
->parent
->color
= 'B';
266 w
->left
->color
= 'B';
267 leftRotate(tree
, node
->parent
);
276 static W_Node
*treeMinimum(W_Node
*node
, W_Node
*nil
)
278 while (node
->left
!= nil
)
284 static W_Node
*treeMaximum(W_Node
*node
, W_Node
*nil
)
286 while (node
->right
!= nil
)
292 static W_Node
*treeSuccessor(W_Node
*node
, W_Node
*nil
)
296 if (node
->right
!= nil
) {
297 return treeMinimum(node
->right
, nil
);
300 while (y
!= nil
&& node
== y
->right
) {
308 static W_Node
*treePredecessor(W_Node
*node
, W_Node
*nil
)
312 if (node
->left
!= nil
) {
313 return treeMaximum(node
->left
, nil
);
316 while (y
!= nil
&& node
== y
->left
) {
324 static W_Node
*rbTreeDelete(W_TreeBag
*tree
, W_Node
*node
)
326 W_Node
*nil
= tree
->nil
;
329 if (node
->left
== nil
|| node
->right
== nil
) {
332 y
= treeSuccessor(node
, nil
);
335 if (y
->left
!= nil
) {
341 x
->parent
= y
->parent
;
343 if (y
->parent
== nil
) {
349 y
->parent
->right
= x
;
353 node
->index
= y
->index
;
354 node
->data
= y
->data
;
356 if (y
->color
== 'B') {
357 rbDeleteFixup(tree
, x
);
365 static W_Node
*treeSearch(W_Node
*root
, W_Node
*nil
, int index
)
367 if (root
== nil
|| root
->index
== index
) {
371 if (index
< root
->index
) {
372 return treeSearch(root
->left
, nil
, index
);
374 return treeSearch(root
->right
, nil
, index
);
379 static W_Node
*treeFind(W_Node
*root
, W_Node
*nil
, void *data
)
383 if (root
== nil
|| root
->data
== data
)
386 tmp
= treeFind(root
->left
, nil
, data
);
390 tmp
= treeFind(root
->right
, nil
, data
);
400 static char buf
[512];
402 static void printNodes(W_Node
*node
, W_Node
*nil
, int depth
)
408 printNodes(node
->left
, nil
, depth
+1);
410 memset(buf
, ' ', depth
*2);
413 printf("%s/(%2i\n", buf
, node
->index
);
415 printf("%s\\(%2i\n", buf
, node
->index
);
417 printNodes(node
->right
, nil
, depth
+1);
421 void PrintTree(WMBag
*bag
)
423 W_TreeBag
*tree
= (W_TreeBag
*)bag
->data
;
425 printNodes(tree
->root
, tree
->nil
, 0);
432 #define SELF ((W_TreeBag*)self->data)
434 WMBag
*WMCreateTreeBag(void)
436 return WMCreateTreeBagWithDestructor(NULL
);
440 WMBag
*WMCreateTreeBagWithDestructor(void (*destructor
)(void*))
445 bag
= wmalloc(sizeof(WMBag
));
447 bag
->data
= tree
= wmalloc(sizeof(W_TreeBag
));
448 memset(tree
, 0, sizeof(W_TreeBag
));
450 tree
->nil
= wmalloc(sizeof(W_Node
));
451 memset(tree
->nil
, 0, sizeof(W_Node
));
452 tree
->nil
->left
= tree
->nil
->right
= tree
->nil
->parent
= tree
->nil
;
453 tree
->nil
->index
= WBNotFound
;
455 tree
->root
= tree
->nil
;
457 bag
->destructor
= destructor
;
459 bag
->func
= bagFunctions
;
465 static int getItemCount(WMBag
*self
)
471 static int appendBag(WMBag
*self
, WMBag
*bag
)
476 for (data
= first(bag
, &ptr
); data
!= NULL
; data
= next(bag
, &ptr
)) {
477 if (!putInBag(self
, data
))
485 static int putInBag(WMBag
*self
, void *item
)
489 ptr
= wmalloc(sizeof(W_Node
));
492 ptr
->index
= SELF
->count
;
493 ptr
->left
= SELF
->nil
;
494 ptr
->right
= SELF
->nil
;
495 ptr
->parent
= SELF
->nil
;
497 rbTreeInsert(SELF
, ptr
);
505 static int insertInBag(WMBag
*self
, int index
, void *item
)
509 ptr
= wmalloc(sizeof(W_Node
));
513 ptr
->left
= SELF
->nil
;
514 ptr
->right
= SELF
->nil
;
515 ptr
->parent
= SELF
->nil
;
517 rbTreeInsert(SELF
, ptr
);
519 while ((ptr
= treeSuccessor(ptr
, SELF
->nil
)) != SELF
->nil
) {
531 static int removeFromBag(WMBag
*self
, void *item
)
533 W_Node
*ptr
= treeFind(SELF
->root
, SELF
->nil
, item
);
535 if (ptr
!= SELF
->nil
) {
540 tmp
= treeSuccessor(ptr
, SELF
->nil
);
541 while (tmp
!= SELF
->nil
) {
543 tmp
= treeSuccessor(tmp
, SELF
->nil
);
546 ptr
= rbTreeDelete(SELF
, ptr
);
557 static int eraseFromBag(WMBag
*self
, int index
)
559 W_Node
*ptr
= treeSearch(SELF
->root
, SELF
->nil
, index
);
561 if (ptr
!= SELF
->nil
) {
565 ptr
= rbTreeDelete(SELF
, ptr
);
575 static int deleteFromBag(WMBag
*self
, int index
)
577 W_Node
*ptr
= treeSearch(SELF
->root
, SELF
->nil
, index
);
579 if (ptr
!= SELF
->nil
) {
584 tmp
= treeSuccessor(ptr
, SELF
->nil
);
585 while (tmp
!= SELF
->nil
) {
587 tmp
= treeSuccessor(tmp
, SELF
->nil
);
590 ptr
= rbTreeDelete(SELF
, ptr
);
600 static void *getFromBag(WMBag
*self
, int index
)
604 node
= treeSearch(SELF
->root
, SELF
->nil
, index
);
605 if (node
!= SELF
->nil
)
613 static int firstInBag(WMBag
*self
, void *item
)
617 node
= treeFind(SELF
->root
, SELF
->nil
, item
);
618 if (node
!= SELF
->nil
)
626 static int treeCount(W_Node
*root
, W_Node
*nil
, void *item
)
633 if (root
->data
== item
)
636 if (root
->left
!= nil
)
637 count
+= treeCount(root
->left
, nil
, item
);
639 if (root
->right
!= nil
)
640 count
+= treeCount(root
->right
, nil
, item
);
647 static int countInBag(WMBag
*self
, void *item
)
649 return treeCount(SELF
->root
, SELF
->nil
, item
);
653 static void *replaceInBag(WMBag
*self
, int index
, void *item
)
655 W_Node
*ptr
= treeSearch(SELF
->root
, SELF
->nil
, index
);
661 ptr
= rbTreeDelete(SELF
, ptr
);
663 } else if (ptr
!= SELF
->nil
) {
669 ptr
= wmalloc(sizeof(W_Node
));
673 ptr
->left
= SELF
->nil
;
674 ptr
->right
= SELF
->nil
;
675 ptr
->parent
= SELF
->nil
;
677 rbTreeInsert(SELF
, ptr
);
688 static int sortBag(WMBag
*self
, int (*comparer
)(const void*, const void*))
695 items
= wmalloc(sizeof(void*)*SELF
->count
);
698 tmp
= treeMinimum(SELF
->root
, SELF
->nil
);
699 while (tmp
!= SELF
->nil
) {
700 items
[i
++] = tmp
->data
;
701 tmp
= treeSuccessor(tmp
, SELF
->nil
);
704 qsort(&items
[0], SELF
->count
, sizeof(void*), comparer
);
707 tmp
= treeMinimum(SELF
->root
, SELF
->nil
);
708 while (tmp
!= SELF
->nil
) {
710 tmp
->data
= items
[i
++];
711 tmp
= treeSuccessor(tmp
, SELF
->nil
);
722 static void deleteTree(WMBag
*self
, W_Node
*node
)
724 if (node
== SELF
->nil
)
727 deleteTree(self
, node
->left
);
729 if (self
->destructor
)
730 self
->destructor(node
->data
);
732 deleteTree(self
, node
->right
);
738 static void emptyBag(WMBag
*self
)
740 deleteTree(self
, SELF
->root
);
741 SELF
->root
= SELF
->nil
;
746 static void freeBag(WMBag
*self
)
755 static void mapTree(W_TreeBag
*tree
, W_Node
*node
,
756 void (*function
)(void*, void*), void *data
)
758 if (node
== tree
->nil
)
761 mapTree(tree
, node
->left
, function
, data
);
763 (*function
)(node
->data
, data
);
765 mapTree(tree
, node
->right
, function
, data
);
769 static void mapBag(WMBag
*self
, void (*function
)(void*, void*), void *data
)
771 mapTree(SELF
, SELF
->root
, function
, data
);
776 static int findInTree(W_TreeBag
*tree
, W_Node
*node
, int (*function
)(void*))
780 if (node
== tree
->nil
)
783 index
= findInTree(tree
, node
->left
, function
);
784 if (index
!= WBNotFound
)
787 if ((*function
)(node
->data
)) {
791 return findInTree(tree
, node
->right
, function
);
795 static int findInBag(WMBag
*self
, int (*match
)(void*))
797 return findInTree(SELF
, SELF
->root
, match
);
803 static void *first(WMBag
*self
, WMBagIterator
*ptr
)
807 node
= treeMinimum(SELF
->root
, SELF
->nil
);
809 if (node
== SELF
->nil
) {
822 static void *last(WMBag
*self
, WMBagIterator
*ptr
)
827 node
= treeMaximum(SELF
->root
, SELF
->nil
);
829 if (node
== SELF
->nil
) {
842 static void *next(WMBag
*self
, WMBagIterator
*ptr
)
849 node
= treeSuccessor(*ptr
, SELF
->nil
);
851 if (node
== SELF
->nil
) {
864 static void *previous(WMBag
*self
, WMBagIterator
*ptr
)
871 node
= treePredecessor(*ptr
, SELF
->nil
);
874 if (node
== SELF
->nil
) {
887 static void *iteratorAtIndex(WMBag
*self
, int index
, WMBagIterator
*ptr
)
891 node
= treeSearch(SELF
->root
, SELF
->nil
, index
);
893 if (node
== SELF
->nil
) {
903 static int indexForIterator(WMBag
*bag
, WMBagIterator ptr
)
905 return ((W_Node
*)ptr
)->index
;