Thu, 30 Oct 2025 19:27:18 +0100
fix typo bug in cxListDifference() - resolves #745
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 1 | /* | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 2 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 3 | * | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 4 | * Copyright 2024 Mike Becker, Olaf Wintermann All rights reserved. | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 5 | * | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 6 | * Redistribution and use in source and binary forms, with or without | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 7 | * modification, are permitted provided that the following conditions are met: | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 8 | * | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 9 | * 1. Redistributions of source code must retain the above copyright | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 10 | * notice, this list of conditions and the following disclaimer. | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 11 | * | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 12 | * 2. Redistributions in binary form must reproduce the above copyright | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 13 | * notice, this list of conditions and the following disclaimer in the | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 14 | * documentation and/or other materials provided with the distribution. | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 15 | * | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 17 | * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 18 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 19 | * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 20 | * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 21 | * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 22 | * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 23 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 24 | * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 25 | * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 26 | * POSSIBILITY OF SUCH DAMAGE. | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 27 | */ | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 28 | |
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 29 | #include "cx/tree.h" | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 30 | |
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 31 | #include "cx/array_list.h" | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 32 | |
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 33 | #include <assert.h> | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 34 | |
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 35 | #define CX_TREE_PTR(cur, off) (*(void**)(((char*)(cur))+(off))) | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 36 | #define tree_parent(node) CX_TREE_PTR(node, loc_parent) | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 37 | #define tree_children(node) CX_TREE_PTR(node, loc_children) | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 38 | #define tree_last_child(node) CX_TREE_PTR(node, loc_last_child) | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 39 | #define tree_prev(node) CX_TREE_PTR(node, loc_prev) | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 40 | #define tree_next(node) CX_TREE_PTR(node, loc_next) | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 41 | |
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 42 | #define cx_tree_ptr_locations \ | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 43 | loc_parent, loc_children, loc_last_child, loc_prev, loc_next | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 44 | |
| 1108 
c3bde8ff1c0b
refine docs for tree.h - issue #548
 Mike Becker <universe@uap-core.de> parents: 
1040diff
changeset | 45 | #define cx_tree_node_layout(tree) \ | 
| 
c3bde8ff1c0b
refine docs for tree.h - issue #548
 Mike Becker <universe@uap-core.de> parents: 
1040diff
changeset | 46 | (tree)->loc_parent,\ | 
| 
c3bde8ff1c0b
refine docs for tree.h - issue #548
 Mike Becker <universe@uap-core.de> parents: 
1040diff
changeset | 47 | (tree)->loc_children,\ | 
| 
c3bde8ff1c0b
refine docs for tree.h - issue #548
 Mike Becker <universe@uap-core.de> parents: 
1040diff
changeset | 48 | (tree)->loc_last_child,\ | 
| 
c3bde8ff1c0b
refine docs for tree.h - issue #548
 Mike Becker <universe@uap-core.de> parents: 
1040diff
changeset | 49 | (tree)->loc_prev, \ | 
| 
c3bde8ff1c0b
refine docs for tree.h - issue #548
 Mike Becker <universe@uap-core.de> parents: 
1040diff
changeset | 50 | (tree)->loc_next | 
| 
c3bde8ff1c0b
refine docs for tree.h - issue #548
 Mike Becker <universe@uap-core.de> parents: 
1040diff
changeset | 51 | |
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 52 | static void cx_tree_zero_pointers( | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 53 | void *node, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 54 | ptrdiff_t loc_parent, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 55 | ptrdiff_t loc_children, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 56 | ptrdiff_t loc_last_child, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 57 | ptrdiff_t loc_prev, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 58 | ptrdiff_t loc_next | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 59 | ) { | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 60 | tree_parent(node) = NULL; | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 61 | if (loc_prev >= 0) { | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 62 | tree_prev(node) = NULL; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 63 | } | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 64 | tree_next(node) = NULL; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 65 | tree_children(node) = NULL; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 66 | if (loc_last_child >= 0) { | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 67 | tree_last_child(node) = NULL; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 68 | } | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 69 | } | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 70 | |
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 71 | void cx_tree_link( | 
| 988 
15b3ca7ee33f
make ucx C++ compatible again (and add tests for it) - fixes #486
 Mike Becker <universe@uap-core.de> parents: 
930diff
changeset | 72 | void *parent, | 
| 
15b3ca7ee33f
make ucx C++ compatible again (and add tests for it) - fixes #486
 Mike Becker <universe@uap-core.de> parents: 
930diff
changeset | 73 | void *node, | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 74 | ptrdiff_t loc_parent, | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 75 | ptrdiff_t loc_children, | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 76 | ptrdiff_t loc_last_child, | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 77 | ptrdiff_t loc_prev, | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 78 | ptrdiff_t loc_next | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 79 | ) { | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 80 | assert(loc_parent >= 0); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 81 | assert(loc_children >= 0); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 82 | assert(loc_next >= 0); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 83 | |
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 84 | void *current_parent = tree_parent(node); | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 85 | if (current_parent == parent) return; | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 86 | if (current_parent != NULL) { | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 87 | cx_tree_unlink(node, cx_tree_ptr_locations); | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 88 | } | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 89 | |
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 90 | if (tree_children(parent) == NULL) { | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 91 | tree_children(parent) = node; | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 92 | if (loc_last_child >= 0) { | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 93 | tree_last_child(parent) = node; | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 94 | } | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 95 | } else { | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 96 | void *child; | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 97 | if (loc_last_child >= 0) { | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 98 | child = tree_last_child(parent); | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 99 | tree_last_child(parent) = node; | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 100 | } else { | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 101 | child = tree_children(parent); | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 102 | void *next; | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 103 | while ((next = tree_next(child)) != NULL) { | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 104 | child = next; | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 105 | } | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 106 | } | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 107 | if (loc_prev >= 0) { | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 108 | tree_prev(node) = child; | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 109 | } | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 110 | tree_next(child) = node; | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 111 | } | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 112 | tree_parent(node) = parent; | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 113 | } | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 114 | |
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 115 | static void *cx_tree_node_prev( | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 116 | ptrdiff_t loc_parent, | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 117 | ptrdiff_t loc_children, | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 118 | ptrdiff_t loc_next, | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 119 | const void *node | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 120 | ) { | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 121 | void *parent = tree_parent(node); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 122 | void *begin = tree_children(parent); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 123 | if (begin == node) return NULL; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 124 | const void *cur = begin; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 125 | const void *next; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 126 | while (1) { | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 127 | next = tree_next(cur); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 128 | if (next == node) return (void *) cur; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 129 | cur = next; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 130 | } | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 131 | } | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 132 | |
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 133 | void cx_tree_unlink( | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 134 | void *node, | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 135 | ptrdiff_t loc_parent, | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 136 | ptrdiff_t loc_children, | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 137 | ptrdiff_t loc_last_child, | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 138 | ptrdiff_t loc_prev, | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 139 | ptrdiff_t loc_next | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 140 | ) { | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 141 | if (tree_parent(node) == NULL) return; | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 142 | |
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 143 | assert(loc_children >= 0); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 144 | assert(loc_next >= 0); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 145 | assert(loc_parent >= 0); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 146 | void *left; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 147 | if (loc_prev >= 0) { | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 148 | left = tree_prev(node); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 149 | } else { | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 150 | left = cx_tree_node_prev(loc_parent, loc_children, loc_next, node); | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 151 | } | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 152 | void *right = tree_next(node); | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 153 | void *parent = tree_parent(node); | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 154 | assert(left == NULL || tree_children(parent) != node); | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 155 | assert(right == NULL || loc_last_child < 0 || | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 156 | tree_last_child(parent) != node); | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 157 | |
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 158 | if (left == NULL) { | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 159 | tree_children(parent) = right; | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 160 | } else { | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 161 | tree_next(left) = right; | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 162 | } | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 163 | if (right == NULL) { | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 164 | if (loc_last_child >= 0) { | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 165 | tree_last_child(parent) = left; | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 166 | } | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 167 | } else { | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 168 | if (loc_prev >= 0) { | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 169 | tree_prev(right) = left; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 170 | } | 
| 862 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 171 | } | 
| 
387414a7afd8
change cx_tree_link() from prepending to appending children - fixes #391
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 172 | |
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 173 | tree_parent(node) = NULL; | 
| 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 174 | tree_next(node) = NULL; | 
| 921 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 175 | if (loc_prev >= 0) { | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 176 | tree_prev(node) = NULL; | 
| 
5a7aa9cf9c3a
make loc_prev in trees optional - fixes #433
 Mike Becker <universe@uap-core.de> parents: 
918diff
changeset | 177 | } | 
| 816 
425234b05dff
add first basic low level tree functions
 Mike Becker <universe@uap-core.de> parents: diff
changeset | 178 | } | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 179 | |
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 180 | int cx_tree_search( | 
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 181 | const void *root, | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 182 | size_t depth, | 
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 183 | const void *node, | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 184 | cx_tree_search_func sfunc, | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 185 | void **result, | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 186 | ptrdiff_t loc_children, | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 187 | ptrdiff_t loc_next | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 188 | ) { | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 189 | // help avoiding bugs due to uninitialized memory | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 190 | assert(result != NULL); | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 191 | *result = NULL; | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 192 | |
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 193 | // remember return value for best match | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 194 | int ret = sfunc(root, node); | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 195 | if (ret < 0) { | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 196 | // not contained, exit | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 197 | return -1; | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 198 | } | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 199 | *result = (void*) root; | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 200 | // if root is already exact match, exit | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 201 | if (ret == 0) { | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 202 | return 0; | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 203 | } | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 204 | |
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 205 | // when depth is one, we are already done | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 206 | if (depth == 1) { | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 207 | return ret; | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 208 | } | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 209 | |
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 210 | // special case: indefinite depth | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 211 | if (depth == 0) { | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 212 | depth = SIZE_MAX; | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 213 | } | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 214 | |
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 215 | // create an iterator | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 216 | CxTreeIterator iter = cx_tree_iterator( | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 217 | (void*) root, false, loc_children, loc_next | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 218 | ); | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 219 | |
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 220 | // skip root, we already handled it | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 221 | cxIteratorNext(iter); | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 222 | |
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 223 | // loop through the remaining tree | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 224 | cx_foreach(void *, elem, iter) { | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 225 | // investigate the current node | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 226 | int ret_elem = sfunc(elem, node); | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 227 | if (ret_elem == 0) { | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 228 | // if found, exit the search | 
| 1286 
5492e8ef05f4
fixes that cx_tree_search() did not investigate subtrees with equally good distance
 Mike Becker <universe@uap-core.de> parents: 
1214diff
changeset | 229 | *result = elem; | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 230 | ret = 0; | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 231 | break; | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 232 | } else if (ret_elem > 0 && ret_elem < ret) { | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 233 | // new distance is better | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 234 | *result = elem; | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 235 | ret = ret_elem; | 
| 1286 
5492e8ef05f4
fixes that cx_tree_search() did not investigate subtrees with equally good distance
 Mike Becker <universe@uap-core.de> parents: 
1214diff
changeset | 236 | } else if (ret_elem < 0 || ret_elem > ret) { | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 237 | // not contained or distance is worse, skip entire subtree | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 238 | cxTreeIteratorContinue(iter); | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 239 | } | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 240 | |
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 241 | // when we reached the max depth, skip the subtree | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 242 | if (iter.depth == depth) { | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 243 | cxTreeIteratorContinue(iter); | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 244 | } | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 245 | } | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 246 | |
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 247 | // dispose the iterator as we might have exited the loop early | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 248 | cxTreeIteratorDispose(&iter); | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 249 | |
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 250 | assert(ret < 0 || *result != NULL); | 
| 826 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 251 | return ret; | 
| 
21840975d541
add cx_tree_search() - relates to #165
 Mike Becker <universe@uap-core.de> parents: 
816diff
changeset | 252 | } | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 253 | |
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 254 | int cx_tree_search_data( | 
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 255 | const void *root, | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 256 | size_t depth, | 
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 257 | const void *data, | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 258 | cx_tree_search_data_func sfunc, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 259 | void **result, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 260 | ptrdiff_t loc_children, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 261 | ptrdiff_t loc_next | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 262 | ) { | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 263 | // it is basically the same implementation | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 264 | return cx_tree_search( | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 265 | root, depth, data, | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 266 | (cx_tree_search_func) sfunc, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 267 | result, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 268 | loc_children, loc_next); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 269 | } | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 270 | |
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 271 | static bool cx_tree_iter_valid(const void *it) { | 
| 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 272 | const struct cx_tree_iterator_s *iter = it; | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 273 | return iter->node != NULL; | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 274 | } | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 275 | |
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 276 | static void *cx_tree_iter_current(const void *it) { | 
| 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 277 | const struct cx_tree_iterator_s *iter = it; | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 278 | return iter->node; | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 279 | } | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 280 | |
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 281 | static void cx_tree_iter_next(void *it) { | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 282 | struct cx_tree_iterator_s *iter = it; | 
| 845 | 283 | ptrdiff_t const loc_next = iter->loc_next; | 
| 284 | ptrdiff_t const loc_children = iter->loc_children; | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 285 | // protect us from misuse | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 286 | if (!iter->base.valid(iter)) return; | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 287 | |
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 288 | void *children; | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 289 | |
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 290 | // check if we are currently exiting or entering nodes | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 291 | if (iter->exiting) { | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 292 | children = NULL; | 
| 848 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 293 | // skipping on exit is pointless, just clear the flag | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 294 | iter->skip = false; | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 295 | } else { | 
| 848 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 296 | if (iter->skip) { | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 297 | // skip flag is set, pretend that there are no children | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 298 | iter->skip = false; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 299 | children = NULL; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 300 | } else { | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 301 | // try to enter the children (if any) | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 302 | children = tree_children(iter->node); | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 303 | } | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 304 | } | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 305 | |
| 836 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 306 | if (children == NULL) { | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 307 | // search for the next node | 
| 1314 
25108c15e2d4
critical: fixes uninitialized memory in tree iterator
 Mike Becker <universe@uap-core.de> parents: 
1309diff
changeset | 308 | void *next = NULL; | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 309 | cx_tree_iter_search_next: | 
| 1309 
b240b73d2a10
fix that iteration continued with siblings for a subtree-root - fixes #656
 Mike Becker <universe@uap-core.de> parents: 
1286diff
changeset | 310 | // check if there is a sibling, but only if we are not a (subtree-)root | 
| 840 
4f02995ce44e
allow freeing tree nodes on exit - fixes #377
 Mike Becker <universe@uap-core.de> parents: 
838diff
changeset | 311 | if (iter->exiting) { | 
| 853 
d4baf4dd55c3
simplify iterator structures
 Mike Becker <universe@uap-core.de> parents: 
848diff
changeset | 312 | next = iter->node_next; | 
| 1309 
b240b73d2a10
fix that iteration continued with siblings for a subtree-root - fixes #656
 Mike Becker <universe@uap-core.de> parents: 
1286diff
changeset | 313 | } else if (iter->depth > 1) { | 
| 840 
4f02995ce44e
allow freeing tree nodes on exit - fixes #377
 Mike Becker <universe@uap-core.de> parents: 
838diff
changeset | 314 | next = tree_next(iter->node); | 
| 853 
d4baf4dd55c3
simplify iterator structures
 Mike Becker <universe@uap-core.de> parents: 
848diff
changeset | 315 | iter->node_next = next; | 
| 840 
4f02995ce44e
allow freeing tree nodes on exit - fixes #377
 Mike Becker <universe@uap-core.de> parents: 
838diff
changeset | 316 | } | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 317 | if (next == NULL) { | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 318 | // no sibling, we are done with this node and exit | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 319 | if (iter->visit_on_exit && !iter->exiting) { | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 320 | // iter is supposed to visit the node again | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 321 | iter->exiting = true; | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 322 | } else { | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 323 | iter->exiting = false; | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 324 | if (iter->depth == 1) { | 
| 836 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 325 | // there is no parent - we have iterated the entire tree | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 326 | // invalidate the iterator and free the node stack | 
| 853 
d4baf4dd55c3
simplify iterator structures
 Mike Becker <universe@uap-core.de> parents: 
848diff
changeset | 327 | iter->node = iter->node_next = NULL; | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 328 | iter->stack_capacity = iter->depth = 0; | 
| 1319 
aa1f580f8f59
add convenience macros for using the default allocator - relates to #669
 Mike Becker <universe@uap-core.de> parents: 
1318diff
changeset | 329 | cxFreeDefault(iter->stack); | 
| 836 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 330 | iter->stack = NULL; | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 331 | } else { | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 332 | // the parent node can be obtained from the top of stack | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 333 | // this way we can avoid the loc_parent in the iterator | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 334 | iter->depth--; | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 335 | iter->node = iter->stack[iter->depth - 1]; | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 336 | // retry with the parent node to find a sibling | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 337 | goto cx_tree_iter_search_next; | 
| 836 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 338 | } | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 339 | } | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 340 | } else { | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 341 | if (iter->visit_on_exit && !iter->exiting) { | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 342 | // iter is supposed to visit the node again | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 343 | iter->exiting = true; | 
| 836 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 344 | } else { | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 345 | iter->exiting = false; | 
| 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 346 | // move to the sibling | 
| 836 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 347 | iter->counter++; | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 348 | iter->node = next; | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 349 | // new top of stack is the sibling | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 350 | iter->stack[iter->depth - 1] = next; | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 351 | } | 
| 838 
1ce90ab4fab9
add visit_on_exit to iterator implementation
 Mike Becker <universe@uap-core.de> parents: 
836diff
changeset | 352 | } | 
| 836 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 353 | } else { | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 354 | // node has children, push the first child onto the stack and enter it | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 355 | cx_array_simple_add(iter->stack, children); | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 356 | iter->node = children; | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 357 | iter->counter++; | 
| 
2672a2f79484
implement basic (enter only) tree iterator
 Mike Becker <universe@uap-core.de> parents: 
834diff
changeset | 358 | } | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 359 | } | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 360 | |
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 361 | CxTreeIterator cx_tree_iterator( | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 362 | void *root, | 
| 833 
5c926801f052
vastly simplify tree iterators and add test for creating them
 Mike Becker <universe@uap-core.de> parents: 
830diff
changeset | 363 | bool visit_on_exit, | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 364 | ptrdiff_t loc_children, | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 365 | ptrdiff_t loc_next | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 366 | ) { | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 367 | CxTreeIterator iter; | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 368 | iter.loc_children = loc_children; | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 369 | iter.loc_next = loc_next; | 
| 833 
5c926801f052
vastly simplify tree iterators and add test for creating them
 Mike Becker <universe@uap-core.de> parents: 
830diff
changeset | 370 | iter.visit_on_exit = visit_on_exit; | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 371 | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 372 | // initialize members | 
| 853 
d4baf4dd55c3
simplify iterator structures
 Mike Becker <universe@uap-core.de> parents: 
848diff
changeset | 373 | iter.node_next = NULL; | 
| 833 
5c926801f052
vastly simplify tree iterators and add test for creating them
 Mike Becker <universe@uap-core.de> parents: 
830diff
changeset | 374 | iter.exiting = false; | 
| 848 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 375 | iter.skip = false; | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 376 | |
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 377 | // assign base iterator functions | 
| 1429 
6e0c3a8a914a
remove the concept of "mutating iterators" - resolves #579
 Mike Becker <universe@uap-core.de> parents: 
1426diff
changeset | 378 | iter.base.allow_remove = false; | 
| 854 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 379 | iter.base.remove = false; | 
| 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 380 | iter.base.current_impl = NULL; | 
| 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 381 | iter.base.valid = cx_tree_iter_valid; | 
| 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 382 | iter.base.next = cx_tree_iter_next; | 
| 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 383 | iter.base.current = cx_tree_iter_current; | 
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 384 | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 385 | // visit the root node | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 386 | iter.node = root; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 387 | if (root != NULL) { | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 388 | iter.stack_capacity = 16; | 
| 1319 
aa1f580f8f59
add convenience macros for using the default allocator - relates to #669
 Mike Becker <universe@uap-core.de> parents: 
1318diff
changeset | 389 | iter.stack = cxMallocDefault(sizeof(void *) * 16); | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 390 | iter.stack[0] = root; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 391 | iter.counter = 1; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 392 | iter.depth = 1; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 393 | } else { | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 394 | iter.stack_capacity = 0; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 395 | iter.stack = NULL; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 396 | iter.counter = 0; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 397 | iter.depth = 0; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 398 | } | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 399 | |
| 830 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 400 | return iter; | 
| 
c4dae6fe6d5b
commit complicated stuff before simplifying it
 Mike Becker <universe@uap-core.de> parents: 
826diff
changeset | 401 | } | 
| 845 | 402 | |
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 403 | static bool cx_tree_visitor_valid(const void *it) { | 
| 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 404 | const struct cx_tree_visitor_s *iter = it; | 
| 845 | 405 | return iter->node != NULL; | 
| 406 | } | |
| 407 | ||
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 408 | static void *cx_tree_visitor_current(const void *it) { | 
| 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 409 | const struct cx_tree_visitor_s *iter = it; | 
| 845 | 410 | return iter->node; | 
| 411 | } | |
| 412 | ||
| 1040 
1ecf4dbbc60c
add some more overflow treatment and make sure to set errno properly
 Mike Becker <universe@uap-core.de> parents: 
989diff
changeset | 413 | cx_attr_nonnull | 
| 845 | 414 | static void cx_tree_visitor_enqueue_siblings( | 
| 415 | struct cx_tree_visitor_s *iter, void *node, ptrdiff_t loc_next) { | |
| 416 | node = tree_next(node); | |
| 417 | while (node != NULL) { | |
| 418 | struct cx_tree_visitor_queue_s *q; | |
| 1319 
aa1f580f8f59
add convenience macros for using the default allocator - relates to #669
 Mike Becker <universe@uap-core.de> parents: 
1318diff
changeset | 419 | q = cxMallocDefault(sizeof(struct cx_tree_visitor_queue_s)); | 
| 845 | 420 | q->depth = iter->queue_last->depth; | 
| 421 | q->node = node; | |
| 422 | iter->queue_last->next = q; | |
| 423 | iter->queue_last = q; | |
| 424 | node = tree_next(node); | |
| 425 | } | |
| 426 | iter->queue_last->next = NULL; | |
| 427 | } | |
| 428 | ||
| 429 | static void cx_tree_visitor_next(void *it) { | |
| 430 | struct cx_tree_visitor_s *iter = it; | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 431 | // protect us from misuse | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 432 | if (!iter->base.valid(iter)) return; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 433 | |
| 845 | 434 | ptrdiff_t const loc_next = iter->loc_next; | 
| 435 | ptrdiff_t const loc_children = iter->loc_children; | |
| 436 | ||
| 848 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 437 | // add the children of the current node to the queue | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 438 | // unless the skip flag is set | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 439 | void *children; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 440 | if (iter->skip) { | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 441 | iter->skip = false; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 442 | children = NULL; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 443 | } else { | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 444 | children = tree_children(iter->node); | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 445 | } | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 446 | if (children != NULL) { | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 447 | struct cx_tree_visitor_queue_s *q; | 
| 1319 
aa1f580f8f59
add convenience macros for using the default allocator - relates to #669
 Mike Becker <universe@uap-core.de> parents: 
1318diff
changeset | 448 | q = cxMallocDefault(sizeof(struct cx_tree_visitor_queue_s)); | 
| 848 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 449 | q->depth = iter->depth + 1; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 450 | q->node = children; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 451 | if (iter->queue_last == NULL) { | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 452 | assert(iter->queue_next == NULL); | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 453 | iter->queue_next = q; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 454 | } else { | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 455 | iter->queue_last->next = q; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 456 | } | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 457 | iter->queue_last = q; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 458 | cx_tree_visitor_enqueue_siblings(iter, children, loc_next); | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 459 | } | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 460 | |
| 845 | 461 | // check if there is a next node | 
| 462 | if (iter->queue_next == NULL) { | |
| 463 | iter->node = NULL; | |
| 464 | return; | |
| 465 | } | |
| 466 | ||
| 467 | // dequeue the next node | |
| 468 | iter->node = iter->queue_next->node; | |
| 469 | iter->depth = iter->queue_next->depth; | |
| 470 | { | |
| 471 | struct cx_tree_visitor_queue_s *q = iter->queue_next; | |
| 472 | iter->queue_next = q->next; | |
| 473 | if (iter->queue_next == NULL) { | |
| 474 | assert(iter->queue_last == q); | |
| 475 | iter->queue_last = NULL; | |
| 476 | } | |
| 1319 
aa1f580f8f59
add convenience macros for using the default allocator - relates to #669
 Mike Becker <universe@uap-core.de> parents: 
1318diff
changeset | 477 | cxFreeDefault(q); | 
| 845 | 478 | } | 
| 479 | ||
| 480 | // increment the node counter | |
| 481 | iter->counter++; | |
| 482 | } | |
| 483 | ||
| 484 | CxTreeVisitor cx_tree_visitor( | |
| 485 | void *root, | |
| 486 | ptrdiff_t loc_children, | |
| 487 | ptrdiff_t loc_next | |
| 488 | ) { | |
| 489 | CxTreeVisitor iter; | |
| 490 | iter.loc_children = loc_children; | |
| 491 | iter.loc_next = loc_next; | |
| 492 | ||
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 493 | // initialize members | 
| 848 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 494 | iter.skip = false; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 495 | iter.queue_next = NULL; | 
| 
6456036bbb37
implement tree continue - fixes #376
 Mike Becker <universe@uap-core.de> parents: 
845diff
changeset | 496 | iter.queue_last = NULL; | 
| 845 | 497 | |
| 498 | // assign base iterator functions | |
| 1429 
6e0c3a8a914a
remove the concept of "mutating iterators" - resolves #579
 Mike Becker <universe@uap-core.de> parents: 
1426diff
changeset | 499 | iter.base.allow_remove = false; | 
| 854 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 500 | iter.base.remove = false; | 
| 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 501 | iter.base.current_impl = NULL; | 
| 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 502 | iter.base.valid = cx_tree_visitor_valid; | 
| 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 503 | iter.base.next = cx_tree_visitor_next; | 
| 
fe0d69d72bcd
fix members inherited by macro or include are not documented
 Mike Becker <universe@uap-core.de> parents: 
853diff
changeset | 504 | iter.base.current = cx_tree_visitor_current; | 
| 845 | 505 | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 506 | // visit the root node | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 507 | iter.node = root; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 508 | if (root != NULL) { | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 509 | iter.counter = 1; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 510 | iter.depth = 1; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 511 | } else { | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 512 | iter.counter = 0; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 513 | iter.depth = 0; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 514 | } | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 515 | |
| 845 | 516 | return iter; | 
| 517 | } | |
| 518 | ||
| 867 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 519 | static void cx_tree_add_link_duplicate( | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 520 | void *original, void *duplicate, | 
| 867 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 521 | ptrdiff_t loc_parent, ptrdiff_t loc_children, ptrdiff_t loc_last_child, | 
| 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 522 | ptrdiff_t loc_prev, ptrdiff_t loc_next | 
| 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 523 | ) { | 
| 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 524 | void *shared_parent = tree_parent(original); | 
| 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 525 | if (shared_parent == NULL) { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 526 | cx_tree_link(original, duplicate, cx_tree_ptr_locations); | 
| 867 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 527 | } else { | 
| 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 528 | cx_tree_link(shared_parent, duplicate, cx_tree_ptr_locations); | 
| 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 529 | } | 
| 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 530 | } | 
| 
471c714d5b6f
cx_tree_add() fix missing spec for adding duplicates
 Mike Becker <universe@uap-core.de> parents: 
866diff
changeset | 531 | |
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 532 | static void cx_tree_add_link_new( | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 533 | void *parent, void *node, cx_tree_search_func sfunc, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 534 | ptrdiff_t loc_parent, ptrdiff_t loc_children, ptrdiff_t loc_last_child, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 535 | ptrdiff_t loc_prev, ptrdiff_t loc_next | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 536 | ) { | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 537 | // check the current children one by one, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 538 | // if they could be children of the new node | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 539 | void *child = tree_children(parent); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 540 | while (child != NULL) { | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 541 | void *next = tree_next(child); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 542 | |
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 543 | if (sfunc(node, child) > 0) { | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 544 | // the sibling could be a child -> re-link | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 545 | cx_tree_link(node, child, cx_tree_ptr_locations); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 546 | } | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 547 | |
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 548 | child = next; | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 549 | } | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 550 | |
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 551 | // add new node as new child | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 552 | cx_tree_link(parent, node, cx_tree_ptr_locations); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 553 | } | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 554 | |
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 555 | int cx_tree_add( | 
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 556 | const void *src, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 557 | cx_tree_search_func sfunc, | 
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 558 | cx_tree_node_create_func cfunc, | 
| 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 559 | void *cdata, | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 560 | void **cnode, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 561 | void *root, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 562 | ptrdiff_t loc_parent, | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 563 | ptrdiff_t loc_children, | 
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 564 | ptrdiff_t loc_last_child, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 565 | ptrdiff_t loc_prev, | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 566 | ptrdiff_t loc_next | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 567 | ) { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 568 | *cnode = cfunc(src, cdata); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 569 | if (*cnode == NULL) return 1; | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 570 | cx_tree_zero_pointers(*cnode, cx_tree_ptr_locations); | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 571 | |
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 572 | void *match = NULL; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 573 | int result = cx_tree_search( | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 574 | root, | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 575 | 0, | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 576 | *cnode, | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 577 | sfunc, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 578 | &match, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 579 | loc_children, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 580 | loc_next | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 581 | ); | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 582 | |
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 583 | if (result < 0) { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 584 | // node does not fit into the tree - return non-zero value | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 585 | return 1; | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 586 | } else if (result == 0) { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 587 | // data already found in the tree, link duplicate | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 588 | cx_tree_add_link_duplicate(match, *cnode, cx_tree_ptr_locations); | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 589 | } else { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 590 | // closest match found, add new node | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 591 | cx_tree_add_link_new(match, *cnode, sfunc, cx_tree_ptr_locations); | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 592 | } | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 593 | |
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 594 | return 0; | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 595 | } | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 596 | |
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 597 | unsigned int cx_tree_add_look_around_depth = 3; | 
| 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 598 | |
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 599 | size_t cx_tree_add_iter( | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 600 | struct cx_iterator_base_s *iter, | 
| 893 
0a2b328f5b91
add bounding parameter to cx_tree_add_iter()
 Mike Becker <universe@uap-core.de> parents: 
890diff
changeset | 601 | size_t num, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 602 | cx_tree_search_func sfunc, | 
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 603 | cx_tree_node_create_func cfunc, | 
| 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 604 | void *cdata, | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 605 | void **failed, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 606 | void *root, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 607 | ptrdiff_t loc_parent, | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 608 | ptrdiff_t loc_children, | 
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 609 | ptrdiff_t loc_last_child, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 610 | ptrdiff_t loc_prev, | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 611 | ptrdiff_t loc_next | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 612 | ) { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 613 | // erase the failed pointer | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 614 | *failed = NULL; | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 615 | |
| 868 
56a908924510
cx_tree_add_iter() - optimize check for empty trees
 Mike Becker <universe@uap-core.de> parents: 
867diff
changeset | 616 | // iter not valid? cancel... | 
| 
56a908924510
cx_tree_add_iter() - optimize check for empty trees
 Mike Becker <universe@uap-core.de> parents: 
867diff
changeset | 617 | if (!iter->valid(iter)) return 0; | 
| 
56a908924510
cx_tree_add_iter() - optimize check for empty trees
 Mike Becker <universe@uap-core.de> parents: 
867diff
changeset | 618 | |
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 619 | size_t processed = 0; | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 620 | void *current_node = root; | 
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 621 | const void *elem; | 
| 868 
56a908924510
cx_tree_add_iter() - optimize check for empty trees
 Mike Becker <universe@uap-core.de> parents: 
867diff
changeset | 622 | |
| 893 
0a2b328f5b91
add bounding parameter to cx_tree_add_iter()
 Mike Becker <universe@uap-core.de> parents: 
890diff
changeset | 623 | for (void **eptr; processed < num && | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 624 | iter->valid(iter) && (eptr = iter->current(iter)) != NULL; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 625 | iter->next(iter)) { | 
| 868 
56a908924510
cx_tree_add_iter() - optimize check for empty trees
 Mike Becker <universe@uap-core.de> parents: 
867diff
changeset | 626 | elem = *eptr; | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 627 | |
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 628 | // create the new node | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 629 | void *new_node = cfunc(elem, cdata); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 630 | if (new_node == NULL) return processed; | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 631 | cx_tree_zero_pointers(new_node, cx_tree_ptr_locations); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 632 | |
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 633 | // start searching from current node | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 634 | void *match; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 635 | int result; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 636 | unsigned int look_around_retries = cx_tree_add_look_around_depth; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 637 | cx_tree_add_look_around_retry: | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 638 | result = cx_tree_search( | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 639 | current_node, | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 640 | 0, | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 641 | new_node, | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 642 | sfunc, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 643 | &match, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 644 | loc_children, | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 645 | loc_next | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 646 | ); | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 647 | |
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 648 | if (result < 0) { | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 649 | // traverse upwards and try to find better parents | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 650 | void *parent = tree_parent(current_node); | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 651 | if (parent != NULL) { | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 652 | if (look_around_retries > 0) { | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 653 | look_around_retries--; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 654 | current_node = parent; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 655 | } else { | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 656 | // look around retries exhausted, start from the root | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 657 | current_node = root; | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 658 | } | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 659 | goto cx_tree_add_look_around_retry; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 660 | } else { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 661 | // no parents. so we failed | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 662 | *failed = new_node; | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 663 | return processed; | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 664 | } | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 665 | } else if (result == 0) { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 666 | // data already found in the tree, link duplicate | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 667 | cx_tree_add_link_duplicate(match, new_node, cx_tree_ptr_locations); | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 668 | // but stick with the original match, in case we needed a new root | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 669 | current_node = match; | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 670 | } else { | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 671 | // closest match found, add new node as child | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 672 | cx_tree_add_link_new(match, new_node, sfunc, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 673 | cx_tree_ptr_locations); | 
| 866 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 674 | current_node = match; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 675 | } | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 676 | |
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 677 | processed++; | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 678 | } | 
| 
1f636de4a63f
complete cx_tree_add() implementations
 Mike Becker <universe@uap-core.de> parents: 
864diff
changeset | 679 | return processed; | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 680 | } | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 681 | |
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 682 | size_t cx_tree_add_array( | 
| 890 
54565fd74e74
move all const keywords to the west - fixes #426
 Mike Becker <universe@uap-core.de> parents: 
871diff
changeset | 683 | const void *src, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 684 | size_t num, | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 685 | size_t elem_size, | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 686 | cx_tree_search_func sfunc, | 
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 687 | cx_tree_node_create_func cfunc, | 
| 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 688 | void *cdata, | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 689 | void **failed, | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 690 | void *root, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 691 | ptrdiff_t loc_parent, | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 692 | ptrdiff_t loc_children, | 
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 693 | ptrdiff_t loc_last_child, | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 694 | ptrdiff_t loc_prev, | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 695 | ptrdiff_t loc_next | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 696 | ) { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 697 | // erase failed pointer | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 698 | *failed = NULL; | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 699 | |
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 700 | // super special case: zero elements | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 701 | if (num == 0) { | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 702 | return 0; | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 703 | } | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 704 | |
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 705 | // special case: one element does not need an iterator | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 706 | if (num == 1) { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 707 | void *node; | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 708 | if (0 == cx_tree_add( | 
| 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 709 | src, sfunc, cfunc, cdata, &node, root, | 
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 710 | loc_parent, loc_children, loc_last_child, | 
| 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 711 | loc_prev, loc_next)) { | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 712 | return 1; | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 713 | } else { | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 714 | *failed = node; | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 715 | return 0; | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 716 | } | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 717 | } | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 718 | |
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 719 | // otherwise, create iterator and hand over to other function | 
| 1429 
6e0c3a8a914a
remove the concept of "mutating iterators" - resolves #579
 Mike Becker <universe@uap-core.de> parents: 
1426diff
changeset | 720 | CxIterator iter = cxIterator(src, elem_size, num, false); | 
| 893 
0a2b328f5b91
add bounding parameter to cx_tree_add_iter()
 Mike Becker <universe@uap-core.de> parents: 
890diff
changeset | 721 | return cx_tree_add_iter(cxIteratorRef(iter), num, sfunc, | 
| 871 
e29c1f96646d
rework cx_tree_add() API to allow insertion of edge nodes
 Mike Becker <universe@uap-core.de> parents: 
870diff
changeset | 722 | cfunc, cdata, failed, root, | 
| 864 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 723 | loc_parent, loc_children, loc_last_child, | 
| 
7d3061f212cb
complete specification for tree_add functions
 Mike Becker <universe@uap-core.de> parents: 
863diff
changeset | 724 | loc_prev, loc_next); | 
| 860 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 725 | } | 
| 
558ed4c6abd0
add prototypes for cx_tree_add() family of functions
 Mike Becker <universe@uap-core.de> parents: 
854diff
changeset | 726 | |
| 904 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 727 | static int cx_tree_default_insert_element( | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 728 | CxTree *tree, | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 729 | const void *data | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 730 | ) { | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 731 | void *node; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 732 | if (tree->root == NULL) { | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 733 | node = tree->node_create(data, tree); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 734 | if (node == NULL) return 1; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 735 | cx_tree_zero_pointers(node, cx_tree_node_layout(tree)); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 736 | tree->root = node; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 737 | tree->size = 1; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 738 | return 0; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 739 | } | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 740 | int result = cx_tree_add(data, tree->search, tree->node_create, | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 741 | tree, &node, tree->root, cx_tree_node_layout(tree)); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 742 | if (0 == result) { | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 743 | tree->size++; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 744 | } else { | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 745 | cxFree(tree->allocator, node); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 746 | } | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 747 | return result; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 748 | } | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 749 | |
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 750 | static size_t cx_tree_default_insert_many( | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 751 | CxTree *tree, | 
| 1214 
ee4e33284f0c
add convenience type CxIteratorBase
 Mike Becker <universe@uap-core.de> parents: 
1109diff
changeset | 752 | CxIteratorBase *iter, | 
| 904 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 753 | size_t n | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 754 | ) { | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 755 | size_t ins = 0; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 756 | if (!iter->valid(iter)) return 0; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 757 | if (tree->root == NULL) { | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 758 | // use the first element from the iter to create the root node | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 759 | void **eptr = iter->current(iter); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 760 | void *node = tree->node_create(*eptr, tree); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 761 | if (node == NULL) return 0; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 762 | cx_tree_zero_pointers(node, cx_tree_node_layout(tree)); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 763 | tree->root = node; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 764 | ins = 1; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 765 | iter->next(iter); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 766 | } | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 767 | void *failed; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 768 | ins += cx_tree_add_iter(iter, n, tree->search, tree->node_create, | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 769 | tree, &failed, tree->root, cx_tree_node_layout(tree)); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 770 | tree->size += ins; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 771 | if (ins < n) { | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 772 | cxFree(tree->allocator, failed); | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 773 | } | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 774 | return ins; | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 775 | } | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 776 | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 777 | static void *cx_tree_default_find( | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 778 | CxTree *tree, | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 779 | const void *subtree, | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 780 | const void *data, | 
| 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 781 | size_t depth | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 782 | ) { | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 783 | if (tree->root == NULL) return NULL; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 784 | |
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 785 | void *found; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 786 | if (0 == cx_tree_search_data( | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 787 | subtree, | 
| 930 
6540096c17b7
add max depth for tree search - closes #459
 Mike Becker <universe@uap-core.de> parents: 
921diff
changeset | 788 | depth, | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 789 | data, | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 790 | tree->search_data, | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 791 | &found, | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 792 | tree->loc_children, | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 793 | tree->loc_next | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 794 | )) { | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 795 | return found; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 796 | } else { | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 797 | return NULL; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 798 | } | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 799 | } | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 800 | |
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 801 | static cx_tree_class cx_tree_default_class = { | 
| 904 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 802 | cx_tree_default_insert_element, | 
| 
cdc49211d87f
implement cxTreeInsert family of functions
 Mike Becker <universe@uap-core.de> parents: 
903diff
changeset | 803 | cx_tree_default_insert_many, | 
| 914 | 804 | cx_tree_default_find | 
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 805 | }; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 806 | |
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 807 | CxTree *cxTreeCreate(const CxAllocator *allocator, | 
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 808 | cx_tree_node_create_func create_func, | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 809 | cx_tree_search_func search_func, | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 810 | cx_tree_search_data_func search_data_func, | 
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 811 | ptrdiff_t loc_parent, ptrdiff_t loc_children, ptrdiff_t loc_last_child, | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 812 | ptrdiff_t loc_prev, ptrdiff_t loc_next | 
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 813 | ) { | 
| 989 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 814 | if (allocator == NULL) { | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 815 | allocator = cxDefaultAllocator; | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 816 | } | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 817 | assert(create_func != NULL); | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 818 | assert(search_func != NULL); | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 819 | assert(search_data_func != NULL); | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 820 | |
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 821 | CxTree *tree = cxMalloc(allocator, sizeof(CxTree)); | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 822 | if (tree == NULL) return NULL; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 823 | |
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 824 | tree->cl = &cx_tree_default_class; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 825 | tree->allocator = allocator; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 826 | tree->node_create = create_func; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 827 | tree->search = search_func; | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 828 | tree->search_data = search_data_func; | 
| 910 
5c2af036103f
fix uninitialized simple_destructor - fixes #443
 Mike Becker <universe@uap-core.de> parents: 
909diff
changeset | 829 | tree->simple_destructor = NULL; | 
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 830 | tree->advanced_destructor = (cx_destructor_func2) cxFree; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 831 | tree->destructor_data = (void *) allocator; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 832 | tree->loc_parent = loc_parent; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 833 | tree->loc_children = loc_children; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 834 | tree->loc_last_child = loc_last_child; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 835 | tree->loc_prev = loc_prev; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 836 | tree->loc_next = loc_next; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 837 | tree->root = NULL; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 838 | tree->size = 0; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 839 | |
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 840 | return tree; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 841 | } | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 842 | |
| 1109 
89ec23988b88
free functions should not be inline in release mode - relates to #541
 Mike Becker <universe@uap-core.de> parents: 
1108diff
changeset | 843 | void cxTreeFree(CxTree *tree) { | 
| 
89ec23988b88
free functions should not be inline in release mode - relates to #541
 Mike Becker <universe@uap-core.de> parents: 
1108diff
changeset | 844 | if (tree == NULL) return; | 
| 
89ec23988b88
free functions should not be inline in release mode - relates to #541
 Mike Becker <universe@uap-core.de> parents: 
1108diff
changeset | 845 | if (tree->root != NULL) { | 
| 
89ec23988b88
free functions should not be inline in release mode - relates to #541
 Mike Becker <universe@uap-core.de> parents: 
1108diff
changeset | 846 | cxTreeClear(tree); | 
| 
89ec23988b88
free functions should not be inline in release mode - relates to #541
 Mike Becker <universe@uap-core.de> parents: 
1108diff
changeset | 847 | } | 
| 
89ec23988b88
free functions should not be inline in release mode - relates to #541
 Mike Becker <universe@uap-core.de> parents: 
1108diff
changeset | 848 | cxFree(tree->allocator, tree); | 
| 
89ec23988b88
free functions should not be inline in release mode - relates to #541
 Mike Becker <universe@uap-core.de> parents: 
1108diff
changeset | 849 | } | 
| 
89ec23988b88
free functions should not be inline in release mode - relates to #541
 Mike Becker <universe@uap-core.de> parents: 
1108diff
changeset | 850 | |
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 851 | CxTree *cxTreeCreateWrapped(const CxAllocator *allocator, void *root, | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 852 | ptrdiff_t loc_parent, ptrdiff_t loc_children, ptrdiff_t loc_last_child, | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 853 | ptrdiff_t loc_prev, ptrdiff_t loc_next) { | 
| 989 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 854 | if (allocator == NULL) { | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 855 | allocator = cxDefaultAllocator; | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 856 | } | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 857 | assert(root != NULL); | 
| 
8aa57a7fecc4
improve consistency for allocator arguments - fixes #485
 Mike Becker <universe@uap-core.de> parents: 
988diff
changeset | 858 | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 859 | CxTree *tree = cxMalloc(allocator, sizeof(CxTree)); | 
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 860 | if (tree == NULL) return NULL; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 861 | |
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 862 | tree->cl = &cx_tree_default_class; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 863 | // set the allocator anyway, just in case... | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 864 | tree->allocator = allocator; | 
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 865 | tree->node_create = NULL; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 866 | tree->search = NULL; | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 867 | tree->search_data = NULL; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 868 | tree->simple_destructor = NULL; | 
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 869 | tree->advanced_destructor = NULL; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 870 | tree->destructor_data = NULL; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 871 | tree->loc_parent = loc_parent; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 872 | tree->loc_children = loc_children; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 873 | tree->loc_last_child = loc_last_child; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 874 | tree->loc_prev = loc_prev; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 875 | tree->loc_next = loc_next; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 876 | tree->root = root; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 877 | tree->size = cxTreeSubtreeSize(tree, root); | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 878 | return tree; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 879 | } | 
| 901 
109567325fe7
add functions to link/unlink nodes manually
 Mike Becker <universe@uap-core.de> parents: 
893diff
changeset | 880 | |
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 881 | void cxTreeSetParent(CxTree *tree, void *parent, void *child) { | 
| 918 | 882 | size_t loc_parent = tree->loc_parent; | 
| 883 | if (tree_parent(child) == NULL) { | |
| 884 | tree->size++; | |
| 885 | } | |
| 886 | cx_tree_link(parent, child, cx_tree_node_layout(tree)); | |
| 887 | } | |
| 888 | ||
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 889 | void cxTreeAddChildNode(CxTree *tree, void *parent, void *child) { | 
| 918 | 890 | cx_tree_link(parent, child, cx_tree_node_layout(tree)); | 
| 891 | tree->size++; | |
| 892 | } | |
| 893 | ||
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 894 | int cxTreeAddChild(CxTree *tree, void *parent, const void *data) { | 
| 901 
109567325fe7
add functions to link/unlink nodes manually
 Mike Becker <universe@uap-core.de> parents: 
893diff
changeset | 895 | void *node = tree->node_create(data, tree); | 
| 
109567325fe7
add functions to link/unlink nodes manually
 Mike Becker <universe@uap-core.de> parents: 
893diff
changeset | 896 | if (node == NULL) return 1; | 
| 
109567325fe7
add functions to link/unlink nodes manually
 Mike Becker <universe@uap-core.de> parents: 
893diff
changeset | 897 | cx_tree_zero_pointers(node, cx_tree_node_layout(tree)); | 
| 
109567325fe7
add functions to link/unlink nodes manually
 Mike Becker <universe@uap-core.de> parents: 
893diff
changeset | 898 | cx_tree_link(parent, node, cx_tree_node_layout(tree)); | 
| 
109567325fe7
add functions to link/unlink nodes manually
 Mike Becker <universe@uap-core.de> parents: 
893diff
changeset | 899 | tree->size++; | 
| 
109567325fe7
add functions to link/unlink nodes manually
 Mike Becker <universe@uap-core.de> parents: 
893diff
changeset | 900 | return 0; | 
| 
109567325fe7
add functions to link/unlink nodes manually
 Mike Becker <universe@uap-core.de> parents: 
893diff
changeset | 901 | } | 
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 902 | |
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 903 | int cxTreeInsert(CxTree *tree, const void *data) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 904 | return tree->cl->insert_element(tree, data); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 905 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 906 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 907 | size_t cxTreeInsertIter(CxTree *tree, CxIteratorBase *iter, size_t n) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 908 | return tree->cl->insert_many(tree, iter, n); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 909 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 910 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 911 | size_t cxTreeInsertArray(CxTree *tree, const void *data, size_t elem_size, size_t n) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 912 | if (n == 0) return 0; | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 913 | if (n == 1) return 0 == cxTreeInsert(tree, data) ? 1 : 0; | 
| 1429 
6e0c3a8a914a
remove the concept of "mutating iterators" - resolves #579
 Mike Becker <universe@uap-core.de> parents: 
1426diff
changeset | 914 | CxIterator iter = cxIterator(data, elem_size, n, false); | 
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 915 | return cxTreeInsertIter(tree, cxIteratorRef(iter), n); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 916 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 917 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 918 | void *cxTreeFind( CxTree *tree, const void *data) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 919 | return tree->cl->find(tree, tree->root, data, 0); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 920 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 921 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 922 | void *cxTreeFindInSubtree(CxTree *tree, const void *data, void *subtree_root, size_t max_depth) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 923 | return tree->cl->find(tree, subtree_root, data, max_depth); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 924 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 925 | |
| 902 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 926 | size_t cxTreeSubtreeSize(CxTree *tree, void *subtree_root) { | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 927 | CxTreeVisitor visitor = cx_tree_visitor( | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 928 | subtree_root, | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 929 | tree->loc_children, | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 930 | tree->loc_next | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 931 | ); | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 932 | while (cxIteratorValid(visitor)) { | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 933 | cxIteratorNext(visitor); | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 934 | } | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 935 | return visitor.counter; | 
| 
5ed7f634f046
implement cxTreeCreate family of functions
 Mike Becker <universe@uap-core.de> parents: 
901diff
changeset | 936 | } | 
| 903 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 937 | |
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 938 | size_t cxTreeSubtreeDepth(CxTree *tree, void *subtree_root) { | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 939 | CxTreeVisitor visitor = cx_tree_visitor( | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 940 | subtree_root, | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 941 | tree->loc_children, | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 942 | tree->loc_next | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 943 | ); | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 944 | while (cxIteratorValid(visitor)) { | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 945 | cxIteratorNext(visitor); | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 946 | } | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 947 | return visitor.depth; | 
| 
a018f5916d3b
add cxTreeSubtreeDepth()
 Mike Becker <universe@uap-core.de> parents: 
902diff
changeset | 948 | } | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 949 | |
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 950 | size_t cxTreeSize(CxTree *tree) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 951 | return tree->size; | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 952 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 953 | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 954 | size_t cxTreeDepth(CxTree *tree) { | 
| 914 | 955 | CxTreeVisitor visitor = cx_tree_visitor( | 
| 956 | tree->root, tree->loc_children, tree->loc_next | |
| 957 | ); | |
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 958 | while (cxIteratorValid(visitor)) { | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 959 | cxIteratorNext(visitor); | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 960 | } | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 961 | return visitor.depth; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 962 | } | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 963 | |
| 913 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 964 | int cxTreeRemoveNode( | 
| 909 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 965 | CxTree *tree, | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 966 | void *node, | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 967 | cx_tree_relink_func relink_func | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 968 | ) { | 
| 908 
f49f8a7060aa
rename cxTreeRemove() to cxTreeRemoveSubtree()
 Mike Becker <universe@uap-core.de> parents: 
907diff
changeset | 969 | if (node == tree->root) return 1; | 
| 
f49f8a7060aa
rename cxTreeRemove() to cxTreeRemoveSubtree()
 Mike Becker <universe@uap-core.de> parents: 
907diff
changeset | 970 | |
| 909 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 971 | // determine the new parent | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 972 | ptrdiff_t loc_parent = tree->loc_parent; | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 973 | void *new_parent = tree_parent(node); | 
| 908 
f49f8a7060aa
rename cxTreeRemove() to cxTreeRemoveSubtree()
 Mike Becker <universe@uap-core.de> parents: 
907diff
changeset | 974 | |
| 909 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 975 | // first, unlink from the parent | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 976 | cx_tree_unlink(node, cx_tree_node_layout(tree)); | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 977 | |
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 978 | // then relink each child | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 979 | ptrdiff_t loc_children = tree->loc_children; | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 980 | ptrdiff_t loc_next = tree->loc_next; | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 981 | void *child = tree_children(node); | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 982 | while (child != NULL) { | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 983 | // forcibly set the parent to NULL - we do not use the unlink function | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 984 | // because that would unnecessarily modify the children linked list | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 985 | tree_parent(child) = NULL; | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 986 | |
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 987 | // update contents, if required | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 988 | if (relink_func != NULL) { | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 989 | relink_func(child, node, new_parent); | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 990 | } | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 991 | |
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 992 | // link to new parent | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 993 | cx_tree_link(new_parent, child, cx_tree_node_layout(tree)); | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 994 | |
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 995 | // proceed to next child | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 996 | child = tree_next(child); | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 997 | } | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 998 | |
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 999 | // clear the linked list of the removed node | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 1000 | tree_children(node) = NULL; | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 1001 | ptrdiff_t loc_last_child = tree->loc_last_child; | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 1002 | if (loc_last_child >= 0) tree_last_child(node) = NULL; | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 1003 | |
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 1004 | // the tree now has one member less | 
| 
f4e00bb3f3b2
implement cxTreeRemove() with re-link function
 Mike Becker <universe@uap-core.de> parents: 
908diff
changeset | 1005 | tree->size--; | 
| 908 
f49f8a7060aa
rename cxTreeRemove() to cxTreeRemoveSubtree()
 Mike Becker <universe@uap-core.de> parents: 
907diff
changeset | 1006 | |
| 
f49f8a7060aa
rename cxTreeRemove() to cxTreeRemoveSubtree()
 Mike Becker <universe@uap-core.de> parents: 
907diff
changeset | 1007 | return 0; | 
| 
f49f8a7060aa
rename cxTreeRemove() to cxTreeRemoveSubtree()
 Mike Becker <universe@uap-core.de> parents: 
907diff
changeset | 1008 | } | 
| 
f49f8a7060aa
rename cxTreeRemove() to cxTreeRemoveSubtree()
 Mike Becker <universe@uap-core.de> parents: 
907diff
changeset | 1009 | |
| 
f49f8a7060aa
rename cxTreeRemove() to cxTreeRemoveSubtree()
 Mike Becker <universe@uap-core.de> parents: 
907diff
changeset | 1010 | void cxTreeRemoveSubtree(CxTree *tree, void *node) { | 
| 907 
1f72fb9af87e
fix bug when removing the root node of a tree
 Mike Becker <universe@uap-core.de> parents: 
905diff
changeset | 1011 | if (node == tree->root) { | 
| 
1f72fb9af87e
fix bug when removing the root node of a tree
 Mike Becker <universe@uap-core.de> parents: 
905diff
changeset | 1012 | tree->root = NULL; | 
| 
1f72fb9af87e
fix bug when removing the root node of a tree
 Mike Becker <universe@uap-core.de> parents: 
905diff
changeset | 1013 | tree->size = 0; | 
| 
1f72fb9af87e
fix bug when removing the root node of a tree
 Mike Becker <universe@uap-core.de> parents: 
905diff
changeset | 1014 | return; | 
| 
1f72fb9af87e
fix bug when removing the root node of a tree
 Mike Becker <universe@uap-core.de> parents: 
905diff
changeset | 1015 | } | 
| 905 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 1016 | size_t subtree_size = cxTreeSubtreeSize(tree, node); | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 1017 | cx_tree_unlink(node, cx_tree_node_layout(tree)); | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 1018 | tree->size -= subtree_size; | 
| 
39aa4f106a71
complete implementation of remaining high level tree functions
 Mike Becker <universe@uap-core.de> parents: 
904diff
changeset | 1019 | } | 
| 913 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1020 | |
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1021 | int cxTreeDestroyNode( | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1022 | CxTree *tree, | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1023 | void *node, | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1024 | cx_tree_relink_func relink_func | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1025 | ) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1026 | int result = cxTreeRemoveNode(tree, node, relink_func); | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1027 | if (result == 0) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1028 | if (tree->simple_destructor) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1029 | tree->simple_destructor(node); | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1030 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1031 | if (tree->advanced_destructor) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1032 | tree->advanced_destructor(tree->destructor_data, node); | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1033 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1034 | return 0; | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1035 | } else { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1036 | return result; | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1037 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1038 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1039 | |
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1040 | void cxTreeDestroySubtree(CxTree *tree, void *node) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1041 | cx_tree_unlink(node, cx_tree_node_layout(tree)); | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1042 | CxTreeIterator iter = cx_tree_iterator( | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1043 | node, true, | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1044 | tree->loc_children, tree->loc_next | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1045 | ); | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1046 | cx_foreach(void *, child, iter) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1047 | if (iter.exiting) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1048 | if (tree->simple_destructor) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1049 | tree->simple_destructor(child); | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1050 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1051 | if (tree->advanced_destructor) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1052 | tree->advanced_destructor(tree->destructor_data, child); | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1053 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1054 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1055 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1056 | tree->size -= iter.counter; | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1057 | if (node == tree->root) { | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1058 | tree->root = NULL; | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1059 | } | 
| 
72db8e42b95e
implement cxTreeDestroyNode and cxTreeDestroySubtree - resolves #438
 Mike Becker <universe@uap-core.de> parents: 
910diff
changeset | 1060 | } | 
| 1426 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1061 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1062 | void cxTreeIteratorDispose(CxTreeIterator *iter) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1063 | cxFreeDefault(iter->stack); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1064 | iter->stack = NULL; | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1065 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1066 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1067 | void cxTreeVisitorDispose(CxTreeVisitor *visitor) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1068 | struct cx_tree_visitor_queue_s *q = visitor->queue_next; | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1069 | while (q != NULL) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1070 | struct cx_tree_visitor_queue_s *next = q->next; | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1071 | cxFreeDefault(q); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1072 | q = next; | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1073 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1074 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1075 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1076 | CxTreeIterator cxTreeIterateSubtree(CxTree *tree, void *node, bool visit_on_exit) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1077 | return cx_tree_iterator( | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1078 | node, visit_on_exit, | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1079 | tree->loc_children, tree->loc_next | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1080 | ); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1081 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1082 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1083 | CxTreeVisitor cxTreeVisitSubtree(CxTree *tree, void *node) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1084 | return cx_tree_visitor( | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1085 | node, tree->loc_children, tree->loc_next | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1086 | ); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1087 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1088 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1089 | CxTreeIterator cxTreeIterate(CxTree *tree, bool visit_on_exit) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1090 | return cxTreeIterateSubtree(tree, tree->root, visit_on_exit); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1091 | } | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1092 | |
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1093 | CxTreeVisitor cxTreeVisit(CxTree *tree) { | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1094 | return cxTreeVisitSubtree(tree, tree->root); | 
| 
3a89b31f0724
clean up header files and adds support for comparing arbitrary strings with string.h functions
 Mike Becker <universe@uap-core.de> parents: 
1319diff
changeset | 1095 | } |