diff --git a/bintree.c b/bintree.c index 5cf82a9..4fc5e59 100644 --- a/bintree.c +++ b/bintree.c @@ -2,17 +2,67 @@ #include "stack.h" #include "bintree.h" -//TODO: binären Suchbaum implementieren +// TODO: binären Suchbaum implementieren /* * `addToTree`: fügt ein neues Element in den Baum ein (rekursiv), - * `clearTree`: gibt den gesamten Baum frei (rekursiv), - * `treeSize`: zählt die Knoten im Baum (rekursiv), - * `nextTreeData`: Traversierung mit Hilfe des zuvor implementierten Stacks. */ + * `clearTree`: gibt den gesamten Baum frei (rekursiv), + * `treeSize`: zählt die Knoten im Baum (rekursiv), + * `nextTreeData`: Traversierung mit Hilfe des zuvor implementierten Stacks. */ // Adds a copy of data's pointer destination to the tree using compareFct for ordering. Accepts duplicates // if isDuplicate is NULL, otherwise ignores duplicates and sets isDuplicate to 1 (or to 0 if a new entry is added). TreeNode *addToTree(TreeNode *root, const void *data, size_t dataSize, CompareFctType compareFct, int *isDuplicate) { + if (isDuplicate) + *isDuplicate = 0; + // Wenn kein Knoten angelegt + if (root == NULL) + { + // Neuen Knoten erstellen + TreeNode *newNode = malloc(sizeof(TreeNode)); + if (!newNode) + return NULL; + // mit Daten füllen + newNode->data = malloc(dataSize); + if (!(newNode->data)) + { + free(newNode); + return NULL; + } + + memcpy(newNode->data, data, dataSize); + newNode->left = NULL; // Kinder NULL setzen + newNode->right = NULL; + return newNode; + } + // auf Doppellungen überprüfen, daten/werte vergelichen + // int cmp = compareFct(data, root->data); + + int cmp = compareFct(data, root->data); + + if (cmp == 0) // Duplikat erkannt + { + if (isDuplicate) // nicht einfügen + { + *isDuplicate = 1; + return root; + } + else // einfügen erlaubt + { + root->right = addToTree(root->right, data, dataSize, compareFct, NULL); + return root; + } + } + // kein Duplikat + if (cmp < 0) + { + root->left = addToTree(root->left, data, dataSize, compareFct, isDuplicate); + } + else if (cmp > 0) + { + root->right = addToTree(root->right, data, dataSize, compareFct, isDuplicate); + } + return root; } // Iterates over the tree given by root. Follows the usage of strtok. If tree is NULL, the next entry of the last tree given is returned in ordering direction. @@ -20,17 +70,64 @@ TreeNode *addToTree(TreeNode *root, const void *data, size_t dataSize, CompareFc // push the top node and push all its left nodes. void *nextTreeData(TreeNode *root) { + static StackNode *stack = NULL; // Stack für Iterator + static TreeNode *lastRoot = NULL; + TreeNode *currentNode; + if (root != NULL) // Initialisierung bei erstem Aufruf + { + lastRoot = root; + + if (stack) + { + freeStack(stack); + stack = NULL; + } + + stack = createStack(); + + // alle linken Knoten vom Wurzelknoten pushen + currentNode = root; + while (currentNode) + { + push(stack, currentNode); + currentNode = currentNode->left; + } + } + // Stack ist leer, keine Daten mehr + if (!stack || isEmpty(stack)) + return NULL; + + TreeNode *newNode = pop(stack); // nächster Knoten + + // Wenn rechter Teilbaum vorhanden → alle linken Knoten pushen + currentNode = newNode->right; + while (currentNode) + { + push(stack, currentNode); + currentNode = currentNode->left; + } + return newNode->data; // Daten zurückgeben } // Releases all memory resources (including data copies). void clearTree(TreeNode *root) { - + if (root) + { + clearTree(root->left); + clearTree(root->right); + free(root->data); + free(root); + } } // Returns the number of entries in the tree given by root. unsigned int treeSize(const TreeNode *root) { - + unsigned int size = 0; + if (root == NULL) + return 0; + size = 1 + treeSize(root->left) + treeSize(root->right); + return size; } \ No newline at end of file