Lecture10 trees v3
-
Upload
hariz-mustafa -
Category
Documents
-
view
434 -
download
0
description
Transcript of Lecture10 trees v3
1
Chapter 10Trees
2
Definition of Tree
• A tree is a set of linked nodes, such that there is one and only one path from a unique node (called the root node) to every other node in the tree.
• A path exists from node A to node B if one can follow a chain of pointers to travel from node A to node B.
3
A
E
F
B
C
D
G
A set of linked nodes
Paths
There is one path from A to B
There is a path from D to B
There is also a second path from D to B.
4
A
E
F
B
C
D
G
There is no path from C to any other node.
Paths (cont.)
5
Cycles
• There is no cycle (circle of pointers) in a tree.
• Any linked structure that has a cycle would have more than one path from the root node to another node.
6
Example of a Cycle
A
C
D
B
E
C → D → B → E → C
7
Tree Cannot Have a Cycle
A
C
D
B
E
2 paths exist from A to C:1. A → C2. A → C → D → B → E → C
8
Example of a Tree
A
C B D
E F G
root
In a tree, every pair of linked nodes have a parent-child relationship (the parent is closer to the root)
9
Example of a Tree(cont.)
A
C B D
E F G
root For example, C is a parent of G
10
Example of a Tree(cont.)
A
C B D
E F G
root E and F are children of D
11
Example of a Tree(cont.)
A
C B D
E F G
root The root node is the only node that has no parent.
12
Example of a Tree(cont.)
A
C B D
E F G
rootLeaf nodes (or leaves for short) have no children.
13
Subtrees
A
B C
I K D E F
J G H
subtree
root A subtree is a part of a tree that is a tree in itself
14
Binary Trees
• A binary tree is a tree in which each node can only have up to two children…
15
NOT a Binary Tree
A
B C
I K D E F
J G H
root C has 3 child nodes.
16
Example of a Binary Tree
A
B C
I K E
J G H
root The links in a tree are often called edges
17
Levels
A
B C
I K E
J G H
rootlevel 0
level 1
level 2
level 3
The level of a node is the number of edges in the path from the root node to this node
18
Full Binary Tree
B
D
H
root
I
A
E
J K
C
F
L M
G
N O
In a full binary tree, each node has two children except for the nodes on the last level, which are leaf nodes
19
Complete Binary Trees
• A complete binary tree is a binary tree that is either– a full binary tree– OR– a tree that would be a full binary tree but it is
missing the rightmost nodes on the last level
20
NOT a Complete Binary Trees
B
D
H
root A
E
C
F G
I Missing non-rightmost nodes on the last level
21
Complete Binary Trees(cont.)
B
D
H
root
I
A
E
J K
C
F
L
G
Missing rightmost nodes on the last level
22
Complete Binary Trees(cont.)
B
D
H
root
I
A
E
J K
C
F
L M
G
N O
A full binary tree is also a complete binary tree.
23
Binary Search Trees
• A binary search tree is a binary tree that allows us to search for values that can be anywhere in the tree.
• Usually, we search for a certain key value, and once we find the node that contains it, we retrieve the rest of the info at that node.
• Therefore, we assume that all values searched for in a binary search tree are distinct.
24
Properties of Binary Search Trees
• A binary search tree does not have to be a complete binary tree.
• For any particular node, – the key in its left child (if any) is less than its
key.– the key in its right child (if any) is greater than
its key.
25
Binary Search Tree Node
template <typename T>BSTNode {
T info;BSTNode<T> *left;BSTNode<T> *right;
};
The implementation of a binary search tree usually just maintains a single pointer in the private section called root, to point to the root node.
26
Inserting Nodes Into a BST
37, 2, 45, 48, 41, 29, 20, 30, 49, 7
Objects that need to be inserted (only key values are shown):
root: NULL
BST starts off empty
27
Inserting Nodes Into a BST (cont.)
37, 2, 45, 48, 41, 29, 20, 30, 49, 7
root 37
28
Inserting Nodes Into a BST (cont.)
2, 45, 48, 41, 29, 20, 30, 49, 7
root 37
2 < 37, so insert 2 on the left side of 37
29
Inserting Nodes Into a BST (cont.)
2, 45, 48, 41, 29, 20, 30, 49, 7
root 37
2
30
Inserting Nodes Into a BST (cont.)
45, 48, 41, 29, 20, 30, 49, 7
root 37
2
45 > 37, so insert it at the right of 37
31
Inserting Nodes Into a BST (cont.)
45, 48, 41, 29, 20, 30, 49, 7
root 37
2 45
32
Inserting Nodes Into a BST (cont.)
48, 41, 29, 20, 30, 49, 7
root 37
2 45
When comparing, we always start at the root node
48 > 37, so look to the right
33
Inserting Nodes Into a BST (cont.)
48, 41, 29, 20, 30, 49, 7
root 37
2 45
This time, there is a node already to the right of the root node. We then compare 48 to this node
48 > 45, and 45 has no right child, so we insert 48 on the right of 45
34
Inserting Nodes Into a BST (cont.)
48, 41, 29, 20, 30, 49, 7
root 37
2 45
48
35
Inserting Nodes Into a BST (cont.)
41, 29, 20, 30, 49, 7
root 37
2 45
4841 > 37, so look to the right
41 < 45, so look to the left – there is no left child, so insert
36
Inserting Nodes Into a BST (cont.)
41, 29, 20, 30, 49, 7
root 37
2 45
4841
37
Inserting Nodes Into a BST (cont.)
29, 20, 30, 49, 7
root 37
2 45
484129 < 37, left
29 > 2, right
38
Inserting Nodes Into a BST (cont.)
29, 20, 30, 49, 7
root 37
2 45
484129
39
Inserting Nodes Into a BST (cont.)
20, 30, 49, 7
root 37
2 45
48412920 < 37, left
20 > 2, right
20 < 29, left
40
Inserting Nodes Into a BST (cont.)
20, 30, 49, 7
root 37
2 45
484129
20
41
Inserting Nodes Into a BST (cont.)
30, 49, 7
root 37
2 45
484129
2030 < 37
30 > 2
30 > 29
42
Inserting Nodes Into a BST (cont.)
30, 49, 7
root 37
2 45
484129
20 30
43
Inserting Nodes Into a BST (cont.)
49, 7
root 37
2 45
484129
20 30
49 > 3749 > 4549 > 48
44
Inserting Nodes Into a BST (cont.)
49, 7
root 37
2 45
484129
20 30 49
45
Inserting Nodes Into a BST (cont.)
7
root 37
2 45
484129
20 30 49
7 < 377 > 27 < 297 < 20
46
Inserting Nodes Into a BST (cont.)
7
root 37
2 45
484129
20 30 49
7
47
Inserting Nodes Into a BST (cont.)
root 37
2 45
484129
20 30 49All elements have been inserted
7
48
Searching for a Key in a BST
root 37
2 45
484129
20 30 49
Searching for a key in a BST uses the same logic
7Key to search for: 29
49
Searching for a Key in a BST (cont.)root
37
2 45
484129
20 30 49
Key to search for: 29
29 < 37
7
50
Searching for a Key in a BST (cont.)root
37
2 45
484129
20 30 49
Key to search for: 29
29 > 2
7
51
Searching for a Key in a BST (cont.)root
37
2 45
484129
20 30 49
Key to search for: 29
29 == 29
FOUND IT!
7
52
Searching for a Key in a BST (cont.)root
37
2 45
484129
20 30 49
Key to search for: 3 7
53
Searching for a Key in a BST (cont.)root
37
2 45
484129
20 30 49
Key to search for: 3
3 < 7
7
3 < 20
3 < 29
3 > 2
3 < 37
54
Searching for a Key in a BST (cont.)root
37
2 45
484129
20 30 49
Key to search for: 3
When the child pointer you want to follow is set to NULL, the key you are looking for is not in the BST
7
55
Deleting a BST Node
• Deleting a node in a BST is a little tricky – it has to be deleted so that the resulting structure is still a BST with each node greater than its left child and less than its right child.
• Deleting a node is handled differently depending on whether the node:– has no children– has one child– has two children
56
Deletion Case 1: No Children
root 37
2 45
484129
20 30 49
Node 49 has no children – to delete it, we just remove it
57
Deletion Case 1: No Children (cont.)
root 37
2 45
484129
20 30
58
Deletion Case 2: One Child
root 37
2 45
484129
20 30 49
Node 48 has one child – to delete it, we just splice it out
59
Deletion Case 2: One Child (cont.)
root 37
2 45
484129
20 30 49
Node 48 has one child – to delete it, we just splice it out
60
Deletion Case 2: One Child (cont.)
root 37
2 45
4129
20 30 49
61
Deletion Case 2: One Child (cont.)
root 37
2 45
484129
20 30 49
Another example: node 2 has one child – to delete it we also splice it out
62
Deletion Case 2: One Child (cont.)
root 37
2 45
484129
20 30 49
Another example: node 2 has one child – to delete it we also splice it out
63
Deletion Case 2: One Child (cont.)
root 37
45
484129
20 30 49
64
Deletion Case 3: Two Children
root 37
2 45
484129
20 30 49
Node 37 has two children…
65
Deletion Case 3: Two Children (cont.)root
37
2 45
484129
20 30 49
to delete it, first we find the greatest node in its left subtree
66
Deletion Case 3: Two Children (cont.)root
37
2 45
484129
20 30 49
First, we go to the left once, then follow the right pointers as far as we can
67
Deletion Case 3: Two Children (cont.)root
37
2 45
484129
20 30 4930 is the greatest node in the left subtree of node 37
68
Deletion Case 3: Two Children (cont.)root
37
2 45
484129
20 30 49Next, we copy the object at node 30 into node 37
69
Deletion Case 3: Two Children (cont.)root
30
2 45
484129
20 49
Finally, we delete the lower red node using case 1 or case 2 deletion
70
Deletion Case 3: Two Children (cont.)root
30
2 45
484129
20 49Let’s delete node 30 now
71
Deletion Case 3: Two Children (cont.)root
30
2 45
484129
20 49
29 is the greatest node in the left subtree of node 30
72
Deletion Case 3: Two Children (cont.)root
30
2 45
484129
20 49
Copy the object at node 29 into node 30
73
Deletion Case 3: Two Children (cont.)root
29
2 45
484129
20 49
This time, the lower red node has a child – to delete it we use case 2 deletion
74
Deletion Case 3: Two Children (cont.)root
29
2 45
484129
20 49
This time, the lower red node has a child – to delete it we use case 2 deletion
75
Deletion Case 3: Two Children (cont.)root
29
2 45
4841
20 49
76
Traversing a BST
• There are 3 ways to traversal a BST (visit every node in BST):
• 1. Preorder (parent → left → right)• 2. Inorder (left → parent → right)• 3. Postorder (left → right → parent)
77
1 template <typename T>2 class BinarySearchTree {3 BSTNode *root;4 void preOrderInternal (BST<T> *parent) { … }5 void inOrderInternal (BST<T> *parent) { … }6 void postOrderInternal (BST<T> *parent) { … }7 void insertInternal (BST<T> *parent, 8 const T& newElement) { … }9 bool searchInternal (const T& target,10 T& foundElement) { … }
Binary Search Tree Class Template
78
11 public:12 BinarySearchTree() { … }13 ~BinarySearchTree() { … }14 bool isEmpty() { … }15 void preOrderTraversal() { … }16 void inOrderTraversal() { … }17 void postOrderTraversal() { … }18 void insert (T element) { … }19 bool search (T element, T& foundElement) { … }20 void makeEmpty() { … }21 }
Binary Search Tree Class Template (cont.)
79
1 BinarySearchTree()2 : root(NULL) { }34 ~BinarySearchTree()5 {6 makeEmpty();7 }8 9 bool isEmpty()10 {11 return root == NULL:12 }
Constructor, Destructor, IsEmpty()
80
2 void inOrderTraversal()3 {4 inOrderInternal (root);5 }
The client uses the driver called InOrderTraversal.
Printing ElementsIn Order
The recursive function inOrderInternal is called. inOrderInternal prints all element in BST in sorted order, starting from root node.
81
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
The base case occurs when parent is NULL – just returns.
Printing ElementsIn Order (cont.)
82
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
There are 2 recursive calls under the if – the first advances the pointer to the left child…
and the second advances the pointer to the right child.
Printing ElementsIn Order (cont.)
83
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
Each recursive call approaches the base case…
it goes down one level through the tree, and it get closer to the case where parent->left or parent->right is NULL.
Printing ElementsIn Order (cont.)
84
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
If the BST contains only one node, the root node is the only node – the left and right pointers of the root node will be set to NULL.
Printing ElementsIn Order (cont.)
85
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
parent->left is NULL, so NULL is passed into parent of the new inOrderInternal function.
Printing ElementsIn Order (cont.)
86
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
Since parent is NULL in the new inOrderInternal function, it will return right away.
Printing ElementsIn Order (cont.)
87
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
parent->right is NULL – thus, the recursive function call immediately returns as before.
Printing ElementsIn Order (cont.)
88
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
Printing ElementsIn Order (cont.)
In fact inOrderInternal works correctly when there is only 0, 1 or many node in the BST.
89
2 void inOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 inOrderInternal (parent->left);6 cout << parent->info << " ";7 inOrderInternal (parent->right);8 }9 }
Printing ElementsIn Order (cont.)
inOrderInternal is called once from the driver inOrderTraversal. Then, for each node in the tree, 2 calls to inOrderInternal are made, giving us a total of 2n + 1 calls where n is the number of nodes.
90
2 void preOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 cout << parent->info << " ";6 preOrderInternal (parent->left);7 preOrderInternal (parent->right);8 }9 }
Printing ElementsPre Order
preOrderInternal prints the parent first.
91
2 void postOrderInternal (BSTNode<T> *parent)3 {4 if (parent != NULL) {5 postOrderInternal (parent->left);6 postOrderInternal (parent->right);7 cout << parent->info << " ";8 }9 }
Printing ElementsPost Order
postOrderInternal prints the parent last.
92
1 bool search (T target, T& foundElement) {2 return searchInternal (root, target, foundElement);3 }45 void insert (const T& newElement) {6 insertInternal (root, newElement);7 }
Searching and Insertion in BST
93
Searching and Insertion in BST
• We can actually figure out searchInternal and insertInternal using the same recursive logic as traversal in BST.
References
• Childs, J. S. (2008). Trees. C++ Classes and Data Structures. Prentice Hall.
94