Tree Traversal (Inorder, Preorder, Postorder)
โก Smart sammanfattning
Trรคdgenomgรฅngar besรถker varje nod i ett binรคrt trรคd i en definierad ordning. Denna resurs fรถrklarar bredd-fรถrst (nivรฅordning) och de tre djup-fรถrst-metoderna โ inorder, preorder och postorder โ med steg-fรถr-steg-exempel, pseudokod och kompletta implementeringar i Python, C och C++.

Vad รคr Tree Traversal?
I trรคddatastrukturen betyder traversering att besรถka noder pรฅ ett specifikt sรคtt. Det finns tvรฅ typer av traverseringar. Generellt sett รคr denna typ av traversering baserad pรฅ det binรคra trรคdet. Ett binรคrt trรคd innebรคr att varje nod kan ha maximalt 2 noder.
Ett binรคrt trรคd รคr en vรคlkรคnd datastruktur. Det finns ocksรฅ ett binรคrt sรถktrรคd (BST). Denna typ av traversering anvรคnds fรถr olika รคndamรฅl. Nivรฅordningsgenomgรฅngen, den anvรคnds fรถr att berรคkna djupet mellan tvรฅ noder. Det finns en annan typ av trรคd som kallas "AVL", dรคr det รคr nรถdvรคndigt att berรคkna hรถjden pรฅ en nod. Vi kan representera ett binรคrt trรคd i arrayen, men fรถr minnesoptimering kommer vi att anvรคnda struktur och pekare fรถr att referera till nรคsta nod.
Typer av trรคdpassering
Som vi diskuterade binรคra trรคd, nu diskuterar vi de enskilda typerna av traverseringar. Beroende pรฅ typerna finns det tvรฅ typer av traversering. Tidigare har vi nรคmnt nรถdvรคndigheten av nivรฅordning eller Breadth-First Traversal. Nu Depth-First Traversal som postorder anvรคnds fรถr radering av en nod (vi kommer att diskutera det senare), preorder anvรคnds fรถr att kopiera ett binรคrt trรคd, och "inorder" kommer att korsa trรคdet pรฅ ett icke-minskande sรคtt.
- Bredd-fรถrsta genomgรฅng
- Depth-First Traversal
- Fรถrbestรคll genomgรฅng
- Genomgรฅng efter order
- Bestรคllningskorsning
Bredd-fรถrsta genomgรฅng
Det รคr ocksรฅ kรคnt som genomgรฅng av nivรฅordning. Lรฅt oss รถvervรคga fรถljande trรคd fรถr att demonstrera nivรฅordningsgenomgรฅngen.
Sรฅ vi bรถrjar frรฅn rotnoden "1". Den kommer att markeras som nivรฅ 1. Sedan kommer algoritmen att gรฅ till alla barn i den aktuella noden. Vi besรถker nod 2 och 3 nu. De kommer att markeras som nivรฅ 2.
Efter det, eftersom vi har 2 noder pรฅ nivรฅ 2, kommer vi att besรถka deras barn ocksรฅ. Sรฅ vi kommer att besรถka 5,6,8,7 och markera dem som nivรฅ 3. Hรคr รคr en sak som inte nรคmns,
Nodens nivรฅ = fรถrรคldernodens nivรฅ + 1
Nivรฅ 1: 1
Nivรฅ 2: 2 3
Nivรฅ 3: 5 6 8 7
En liknande algoritm anvรคnds fรถr BFS (Utรถka fรถrsta sรถkningen).
Hรคr รคr pseudokoden fรถr genomgรฅng av nivรฅordning:
level_order(node)
Q โ Queue()
Q.push(node)
while !Q.empty():
current_node = Q.pop()
print current_node.value
# Checking if the current node have any child or not
if current_node.left is not NULL:
Q.push(current_node.left)
if current_node.right is not NULL:
Q.push(current_node.right)
Inorder Traversal binรคrt trรคd
Lรฅt oss ta samma exempel som tidigare. I denna typ av traversering besรถker vi fรถrst det vรคnstra undertrรคdet, sedan roten och efter det det hรถgra undertrรคdet. Fรถr att gรถra det lรคttare att komma ihรฅg kan vi sรคga att det gรฅr som vรคnster-rot-hรถger.
Fรถr hela trรคdet, lรฅt oss sรคga att roten รคr 1. Nu fรถljer algoritmen:
- Besรถk det vรคnstra undertrรคdet av nod 1.
- Den nuvarande noden รคr 2 (eftersom det รคr det vรคnstra undertrรคdet av 1)
- Besรถk det vรคnstra undertrรคdet av 2. Den aktuella noden kommer att vara 5 denna gรฅng.
- Flytta till 5, det har inga barn, sรฅ nod 5 kommer att markeras som besรถkt. Den kommer att รฅtergรฅ till fรถrรคldranoden; vilket รคr 2.
- Eftersom det vรคnstra undertrรคdet av 2 besรถks, kommer nu 2 att besรถkas ocksรฅ.
- Ocuco-landskapet algoritm kommer att flytta den aktuella noden till hรถger undertrรคd av nod 2, vilket รคr nod 6. Efter att ha besรถkt nod 6. Den kommer att flytta till sin รถverordnade nod 2.
- Nรคr nod 2 besรถks kommer vi nu att besรถka fรถrรคldern till 2; som รคr nod 1.
- Efter det kommer vi att besรถka det hรถgra undertrรคdet.
Sรฅ den sista genomgรฅngen kommer att se ut sรฅ hรคr:
I ordning: 5 โ 2 โ 6 โ 1 โ 8 โ 3 โ 7
Hรคr รคr pseudokoden fรถr in-order-traversal:
InOrder(node):
if node is not null:
InOrder(node.left)
print node.value
InOrder(node.right)
Detta รคr den rekursiva algoritmen fรถr รถvergรฅngen av oordning. Fรถr Binรคrt sรถktrรคd (BST), Inorder-traversal ger den sorterade matrisen av vรคrden.
Traversering efter bestรคllning
I den hรคr genomgรฅngen kommer vi att korsa undertrรคdet lรคngst till vรคnster fรถrst, sedan undertrรคdet lรคngst till hรถger efter roten. Alla รถvergรฅngar kommer att vara i Post-Order. Lรฅt oss visa ett exempel:
Hรคr fรถr rot = 1,
- Vi gรฅr fรถrst till vรคnster undertrรคd. Sรฅ roten blir 2.
- Dรฅ har 2 lรคmnat undertrรคdet, sรฅ vi gรฅr till nod 5. Nu รคr roten 5.
- Det har inget vรคnster undertrรคd, det har inte heller nรฅgot hรถger undertrรคd. Sรฅ nu kommer vi att markera nod 5 som besรถkt och vi gรฅr till dess รถverordnade nod.
- Nu รคr roten 2 och dess vรคnstra undertrรคd รคr helt besรถkt. Vi kommer nu att flytta till dess hรถgra undertrรคd. Sรฅ roten blir 6.
- Eftersom nod 6 inte har nรฅgot vรคnster och hรถger undertrรคd, kommer vi att markera nod 6 som besรถkt och flytta till dess รถverordnade nod 2.
- Nu besรถks bรฅde vรคnster och hรถger undertrรคd fรถr nod 2. Det kommer ocksรฅ att markeras som besรถkt.
- Vi flyttar till fรถrรคldern till nod 2, som รคr nod 1.
- Det vรคnstra undertrรคdet besรถks fรถr rot 1. Pรฅ samma sรคtt kommer vi nu att besรถka det hรถgra undertrรคdet.
Cirkeln markerad รคr det hรถgra undertrรคdet. Nu kommer vi att besรถka det hรถgra undertrรคdet som vi besรถkte det vรคnstra undertrรคdet. Efter det kommer vi att besรถka noden. Sรฅ den sista genomgรฅngen blir:
Postorder: 5 โ 6 โ 2 โ 8 โ 7 โ 3 โ 1
Hรคr รคr pseudokoden fรถr genomgรฅng av postorder:
PostOrder(node):
if node is not null:
PostOrder(node.left)
PostOrder(node.right)
print node.value
Fรถrbestรคllningstrafik
Fรถr fรถrbestรคllningsgenomgรฅngen kommer algoritmen att besรถka rotnoden fรถrst, efter det kommer den att flyttas till vรคnster respektive hรถger undertrรคd. Fรถr att underlรคtta fรถrstรฅelsen kan vi tรคnka pรฅ fรถrbestรคllning av genomgรฅngsbesรถk som rot โ vรคnster-hรถger.
Sรฅ lรฅt oss vรคlja nod 1 som rot.
- Enligt algoritmen kommer roten att upptรคckas fรถrst, sedan det vรคnstra och sedan det hรถgra undertrรคdet.
- Sรฅ vi besรถker rot 1. Sedan flyttar vi till dess vรคnstra undertrรคd. Roten blir 2.
- Vi besรถker nod 2 och gรฅr vidare till dess vรคnstra undertrรคd. Sรฅ roten blir 3.
- Vi besรถker nod 3, sedan flyttar vi till dess modernod. Nu besรถks nod 2 och dess vรคnstra undertrรคd. Dags att besรถka rรคtt undertrรคd.
- Vi flyttar till hรถger undertrรคd, roten blir 4. Vi besรถker 4. Eftersom 4 inte har nรฅgon underordnad nod, flyttar vi till dess fรถrรคlder.
- Nu รคr roten 2 och den besรถks tillsammans med dess vรคnstra och hรถgra undertrรคd. Sรฅ vi flyttar till dess รถverordnade nod. Nu blir root 1.
- Pรฅ samma sรคtt kommer vi att besรถka det hรถgra undertrรคdet.
Fรถrbestรคllning: 1 โ 2 โ 3 โ 4 โ 5 โ 6 โ 7
Hรคr รคr pseudokoden fรถr fรถrbestรคllningstraversering:
PreOrder(node):
if node is not null:
print node.value
PreOrder(node.left)
PreOrder(node.right)
Genomfรถrande i Python
class Node: def __init__(self, item): self.left = None self.right = None self.val = item # creating a tree data structure def inorder(root): #checking if the root is null or not if root: inorder(root.left) # recursively calling left subtree print(str(root.val) + " ", end = '') inorder(root.right) # recursively calling right subtree def postorder(root): if root: postorder(root.left) postorder(root.right) print(str(root.val) + " ", end = '') def preorder(root): if root: print(str(root.val) + " ", end = '') preorder(root.left) preorder(root.right) def levelOrder(root): queue = list() queue.append(root) while len(queue) > 0: current = queue[0] queue = queue[1: ] print(str(current.val) + " ", end = "") if current.left: queue.append(current.left) if current.right: queue.append(current.right) root = Node(1) root.left = Node(2) root.right = Node(3) root.left.left = Node(4) root.left.right = Node(5) root.right.left = Node(6) root.right.right = Node(7) print("\nLevelOrder traversal:\t", end = " ") levelOrder(root) print("\nInorder traversal:\t", end = " ") inorder(root) print("\nPreorder traversal:\t", end = " ") preorder(root) print("\nPostorder traversal:\t", end = " ") postorder(root)
Produktion:
LevelOrder traversal: 1 2 3 4 5 6 7 Inorder traversal: 4 2 5 1 6 3 7 Preorder traversal: 1 2 4 5 3 6 7 Postorder traversal: 4 5 2 6 7 3 1
Implementering i C
#include <stdio.h> #include <stdlib.h> struct node { int value; struct node* left; struct node* right; }; // Inorder traversal void InOrder(struct node* root) { if (root == NULL) return; InOrder(root->left); printf("%d ", root->value); InOrder(root->right); } // PreOrder traversal void PreOrder(struct node* root) { if (root == NULL) return; printf("%d ", root->value); PreOrder(root->left); PreOrder(root->right); } // PostOrder traversal void PostOrder(struct node* root) { if (root == NULL) return; PostOrder(root->left); PostOrder(root->right); printf("%d ", root->value); } // Create a new Node struct node* createNode(int value) { struct node* newNode = malloc(sizeof(struct node)); newNode->value = value; newNode->left = NULL; newNode->right = NULL; return newNode; } int main() { struct node* root = createNode(1); root->left = createNode(2); root->right = createNode(3); root->left->left = createNode(4); root->left->right = createNode(5); root->right->left = createNode(6); root->right->right = createNode(7); printf("Inorder traversal:\t"); InOrder(root); printf("\PreOrder traversal:\t"); PreOrder(root); printf("\nPostOrder traversal:\t"); PostOrder(root); }
Produktion:
Inorder traversal: 4 2 5 1 6 3 7 Preorder traversal: 1 2 4 5 3 6 7 Postorder traversal: 4 5 2 6 7 3 1
Infรถrande av C++ (Anvรคnder std::queue fรถr nivรฅordning)
#include <stdio.h> #include <stdlib.h> #include<queue> typedef struct node { int value; struct node* left; struct node* right; }node; // Inorder traversal void InOrder(struct node* root) { if (root == NULL) return; InOrder(root->left); printf("%d ", root->value); InOrder(root->right); } // PreOrder traversal void PreOrder(struct node* root) { if (root == NULL) return; printf("%d ", root->value); PreOrder(root->left); PreOrder(root->right); } // PostOrder traversal void PostOrder(struct node* root) { if (root == NULL) return; PostOrder(root->left); PostOrder(root->right); printf("%d ", root->value); } void LevelOrder(struct node* root){ std::queue<struct node*> Q; Q.push(root); while(!Q.empty()){ struct node* current = Q.front(); Q.pop(); printf("%d ",current->value); if(current->left) Q.push(current->left); if(current->right) Q.push(current->right); } } // Create a new Node struct node* createNode(int value) { struct node* newNode = new node(); newNode->value = value; newNode->left = NULL; newNode->right = NULL; return newNode; } int main() { struct node* root = createNode(1); root->left = createNode(2); root->right = createNode(3); root->left->left = createNode(4); root->left->right = createNode(5); root->right->left = createNode(6); root->right->right = createNode(7); printf("Level Order traversal:\t"); LevelOrder(root); printf("\nInorder traversal:\t"); InOrder(root); printf("\nPreOrder traversal:\t"); PreOrder(root); printf("\nPostOrder traversal:\t"); PostOrder(root); }
LevelOrder traversal: 1 2 3 4 5 6 7 Inorder traversal: 4 2 5 1 6 3 7 Preorder traversal: 1 2 4 5 3 6 7 Postorder traversal: 4 5 2 6 7 3 1






