src/cx/tree.h

changeset 833
5c926801f052
parent 830
c4dae6fe6d5b
child 835
13068743197f
--- a/src/cx/tree.h	Sun Feb 18 13:16:38 2024 +0100
+++ b/src/cx/tree.h	Sun Feb 18 13:38:42 2024 +0100
@@ -45,28 +45,6 @@
 #endif
 
 /**
- * When entering a node.
- *
- * When this is the first sibling, source is the parent, otherwise it is the previous child.
- */
-#define CX_TREE_ITERATOR_ENTER      0x1
-/**
- * When advancing to the next child.
- *
- * The visited node is the next child and the source is the previous child.
- * This pass is triggered after exiting the previous child and before entering the next child.
- */
-#define CX_TREE_ITERATOR_NEXT_CHILD 0x2
-/**
- * When exiting the node.
- *
- * The visited node is the node being exited and source is the previously entered node
- * (usually the last child of the exited node, unless it has no children, in which case it is the node itself).
- * When advancing to the next child in a list of siblings, the previous child is exited, first.
- */
-#define CX_TREE_ITERATOR_EXIT       0x4
-
-/**
  * Tree iterator.
  *
  * This iterator is not position-aware in a strict sense, as it does not assume a particular order of elements in the
@@ -74,9 +52,8 @@
  * Each node, regardless of the number of passes, is counted only once.
  *
  * @note Objects that are pointed to by an iterator are mutable through that iterator. However, if the
- * iterator is based on a collection and the underlying collection is mutated by other means than this iterator
- * (e.g. elements added or removed), the iterator becomes invalid (regardless of what cxIteratorValid() returns)
- * and MUST be re-obtained from the collection.
+ * underlying data structure is mutated by other means than this iterator (e.g. elements added or removed),
+ * the iterator becomes invalid (regardless of what cxIteratorValid() returns).
  *
  * @see CxIterator
  */
@@ -86,20 +63,14 @@
      */
     struct cx_iterator_base_s base;
     /**
-     * The passes that are requested by this iterator.
-     * A combination of the flags #CX_TREE_ITERATOR_ENTER, #CX_TREE_ITERATOR_NEXT_CHILD, #CX_TREE_ITERATOR_EXIT.
-     *
-     * Changing the value after beginning the iteration is unspecified.
+     * Set to true, when the iterator shall visit a node again
+     * when all it's children have been processed.
      */
-    uint8_t requested_passes;
+    bool visit_on_exit;
     /**
-     * The current pass.
-     *
-     * @see CX_TREE_ITERATOR_ENTER
-     * @see CX_TREE_ITERATOR_NEXT_CHILD
-     * @see CX_TREE_ITERATOR_EXIT
+     * True, if this iterator is currently leaving the node.
      */
-    uint8_t current_pass;
+    bool exiting;
     /**
      * Offset in the node struct for the children linked list.
      */
@@ -119,14 +90,6 @@
      */
     void *node;
     /**
-     * The node where we came from.
-     *
-     * - When entering the root node, this is \c NULL.
-     * - When entering another node, this is the node's parent.
-     * - When advancing to the next child, this is the previous child.
-     */
-    void *source;
-    /**
      * Internal stack.
      * Will be automatically freed once the iterator becomes invalid.
      *
@@ -138,10 +101,16 @@
      * Internal capacity of the stack.
      */
     size_t stack_capacity;
-    /**
-     * Current depth.
-     */
-    size_t depth;
+    union {
+        /**
+         * Internal stack size.
+         */
+        size_t stack_size;
+        /**
+         * The current depth in the tree.
+         */
+        size_t depth;
+    };
 } CxTreeIterator;
 
 /**
@@ -261,17 +230,6 @@
 /**
  * Creates an iterator for a tree with the specified root node.
  *
- * The \p passes argument is supposed to be a combination of the flags
- * #CX_TREE_ITERATOR_ENTER, #CX_TREE_ITERATOR_NEXT_CHILD, and #CX_TREE_ITERATOR_EXIT.
- * Alternatively, the integer 1 is equivalent to just specifying #CX_TREE_ITERATOR_ENTER
- * which will cause the iterator to pass every node only once (when entering the node).
- *
- * When #CX_TREE_ITERATOR_EXIT is set, the iterator will visit a parent node again,
- * when \em every of it's children has been visited (including the case when the node does not have any children).
- *
- * When #CX_TREE_ITERATOR_NEXT_CHILD is set, the iterator will visit a parent node again,
- * when advancing from one child to the next.
- *
  * @note A tree iterator needs to maintain a stack of visited nodes, which is allocated using stdlib malloc().
  * When the iterator becomes invalid, this memory is automatically released. However, if you wish to cancel the
  * iteration before the iterator becomes invalid by itself, you MUST call cxTreeIteratorDispose() manually to release
@@ -280,7 +238,7 @@
  * @remark At the moment, the returned iterator does not support cxIteratorFlagRemoval().
  *
  * @param root the root node
- * @param passes the passes this iterator shall perform
+ * @param visit_on_exit set to true, when the iterator shall visit a node again after processing all children
  * @param loc_children offset in the node struct for the children linked list
  * @param loc_next offset in the node struct for the next pointer
  * @return the new tree iterator
@@ -289,7 +247,7 @@
 __attribute__((__nonnull__))
 CxTreeIterator cx_tree_iterator(
         void *root,
-        int passes,
+        bool visit_on_exit,
         ptrdiff_t loc_children,
         ptrdiff_t loc_next
 );

mercurial