From a7f5d493bbc27e8c446161d15fb137dd4b33d476 Mon Sep 17 00:00:00 2001 From: theonlybigmiao <2365609100@qq.com> Date: Sun, 10 Nov 2024 18:03:16 +0800 Subject: [PATCH] update the non-recursion ways of binary tree --- .../README.md | 36 +++++ .../program.c | 144 ++++++++++++++++++ 2 files changed, 180 insertions(+) create mode 100644 Binary Tree Algorithms/Non-Recursion Traversal Algorithms/README.md create mode 100644 Binary Tree Algorithms/Non-Recursion Traversal Algorithms/program.c diff --git a/Binary Tree Algorithms/Non-Recursion Traversal Algorithms/README.md b/Binary Tree Algorithms/Non-Recursion Traversal Algorithms/README.md new file mode 100644 index 00000000..f399efce --- /dev/null +++ b/Binary Tree Algorithms/Non-Recursion Traversal Algorithms/README.md @@ -0,0 +1,36 @@ +# Non-Recursive Binary Tree Traversal + +This section describes the implementation of functions in C that performs non-recursive traversal of a binary tree. Here offers pre-order, in-order, and post-order traversals. + +## Problem Statement +Given a binary tree, implement pre-order, in-order, and post-order traversals of the tree in a non-recursive manner. + +## Solution +To perform non-recursive traversal of a binary tree, we utilize a stack data structure. The `StackNode` struct is essential as it allows us to keep track of the nodes during traversal. Each `StackNode` contains a pointer to a `Node` of the binary tree and a pointer to the next `StackNode`, mimicking the Last-In-First-Out (LIFO) behavior of a stack. + +### 1. pre-order Traversal +In pre-order traversal, we visit the root node first, then recursively perform pre-order traversal on the left subtree, and finally on the right subtree. + +**Implementation Details:** +- Initialize an empty stack and push the root node onto the stack. +- Pop a node from the stack, visit it, and push its right child followed by its left child onto the stack. +- Repeat the process until the stack is empty. + +### 2. in-order Traversal +In in-order traversal, we recursively perform in-order traversal on the left subtree, visit the root node, and then recursively perform in-order traversal on the right subtree. + +**Implementation Details:** +- Initialize an empty stack and set the current node to the root. +- Push all left children of the current node onto the stack until a leaf node is reached. +- Pop a node from the stack, visit it, set the current node to its right child, and repeat the process. +- If the current node is NULL and the stack is empty, the traversal is complete. + +### 3. post-order Traversal +In post-order traversal, we recursively perform post-order traversal on the left subtree, then on the right subtree, and finally visit the root node. + +**Implementation Details:** +- Initialize two stacks, `stack1` and `stack2`. +- Push the root node onto `stack1`. +- Pop a node from `stack1`, push it onto `stack2`, and then push its left child followed by its right child onto `stack1`. +- Repeat the process until `stack1` is empty. +- Pop nodes from `stack2` and visit them, which will be in post-order since the last nodes to be popped from `stack1` are the leftmost nodes. \ No newline at end of file diff --git a/Binary Tree Algorithms/Non-Recursion Traversal Algorithms/program.c b/Binary Tree Algorithms/Non-Recursion Traversal Algorithms/program.c new file mode 100644 index 00000000..1df42380 --- /dev/null +++ b/Binary Tree Algorithms/Non-Recursion Traversal Algorithms/program.c @@ -0,0 +1,144 @@ +#include +#include + + +typedef struct Node { + int data; + struct Node *left; + struct Node *right; +} Node; + + +typedef struct StackNode { + Node *treeNode; + // Pointer to the next stack node + struct StackNode *next; +} StackNode; + +// Function to create a new node +Node* newNode(int data) { + Node *node = (Node *)malloc(sizeof(Node)); + node->data = data; + node->left = NULL; + node->right = NULL; + return node; +} + +// Function to create a new stack node +StackNode* newStackNode(Node *treeNode) { + StackNode *stackNode = (StackNode *)malloc(sizeof(StackNode)); + stackNode->treeNode = treeNode; + stackNode->next = NULL; + return stackNode; +} + +// Function to check if the stack is empty +int isStackEmpty(StackNode *top) { + return top == NULL; +} + +// Function to push a node onto the stack +void push(StackNode **top, Node *treeNode) { + StackNode *newStackNode = (StackNode *)malloc(sizeof(StackNode)); + newStackNode->treeNode = treeNode; + newStackNode->next = *top; + *top = newStackNode; +} + +// Function to pop a node from the stack +Node* pop(StackNode **top) { + if (isStackEmpty(*top)) { + return NULL; + } + StackNode *temp = *top; + Node *treeNode = temp->treeNode; + *top = temp->next; + free(temp); + return treeNode; +} + +// Function to get the top node of the stack +Node* top(StackNode *top) { + if (isStackEmpty(top)) { + return NULL; + } + return top->treeNode; +} + +// Function to perform preorder traversal of the tree +void preorderTraversal(Node *root) { + if (root == NULL) return; + StackNode *stack = NULL; + // Push the root node onto the stack + push(&stack, root); + while (!isStackEmpty(stack)) { + Node *current = pop(&stack); + // Print the data + printf("%d ", current->data); + if (current->right) push(&stack, current->right); + if (current->left) push(&stack, current->left); + } +} + +// Function to perform inorder traversal of the tree +void inorderTraversal(Node *root) { + if (root == NULL) return; + StackNode *stack = NULL; + Node *current = root; + while (current != NULL || !isStackEmpty(stack)) { + while (current != NULL) { + // Push nodes onto the stack + push(&stack, current); + // Move to the left child + current = current->left; + } + current = pop(&stack); + printf("%d ", current->data); + // Move to the right child + current = current->right; + } +} + +// Function to perform postorder traversal of the tree +void postorderTraversal(Node *root) { + if (root == NULL) return; + // Initialize stack1 + StackNode *stack1 = NULL; + // Initialize stack2 + StackNode *stack2 = NULL; + // Push the root node onto stack1 + push(&stack1, root); + while (!isStackEmpty(stack1)) { + Node *current = pop(&stack1); + // Push the node onto stack2 + push(&stack2, current); + // Push left child if it exists + if (current->left) push(&stack1, current->left); + // Push right child if it exists + if (current->right) push(&stack1, current->right); + } + while (!isStackEmpty(stack2)) { + // Pop a node from stack2 + Node *current = pop(&stack2); + printf("%d ", current->data); + } +} + +// Main function to demonstrate tree traversals +int main() { + Node* root = newNode(10); + root->left = newNode(5); + root->right = newNode(20); + root->left->left = newNode(3); + root->left->right = newNode(8); + printf("Preorder traversal: "); + preorderTraversal(root); + printf("\n"); + printf("Inorder traversal: "); + inorderTraversal(root); + printf("\n"); + printf("Postorder traversal: "); + postorderTraversal(root); + printf("\n"); + return 0; +} \ No newline at end of file