0% found this document useful (0 votes)
8 views47 pages

03 - APS - Tree

The document provides an overview of tree data structures, including definitions, basic terms, and types such as binary trees and binary search trees. It explains key concepts such as node relationships, tree height, and properties of binary trees, along with search algorithms for binary search trees. Additionally, it details procedures for searching, finding minimum and maximum keys, and understanding tree structures in a hierarchical manner.

Uploaded by

kgztjmqsss
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
8 views47 pages

03 - APS - Tree

The document provides an overview of tree data structures, including definitions, basic terms, and types such as binary trees and binary search trees. It explains key concepts such as node relationships, tree height, and properties of binary trees, along with search algorithms for binary search trees. Additionally, it details procedures for searching, finding minimum and maximum keys, and understanding tree structures in a hierarchical manner.

Uploaded by

kgztjmqsss
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 47

Algorithms & data structures

Tree
Damjan Strnad
2

Tree data structure



a tree is a hierarchical data structure in which each
element can have multiple successors but only one
parent

it allows efficient storage of ordered data and operations
on them

in graph theory a tree is a connected acyclic graph
3

Tree data structure



a tree T is a finite nonempty set of nodes from which
one node is special (i.e., a root), while other nodes
form a disjunctive union of n trees T1, T2, . . . , Tn , where
n>0

we visualize a tree by drawing it downwards from the
root node on top

example: descendant tree of a person named Janez
4

Tree – basic terms



a node v∈T has arbitrary number of children; that
number is called degree of node v and corresponds to
the number of subtrees in node v

a node with degree 0 (i.e., a node with no children) is a
leaf; nodes that are not leaves are inner nodes

every node except the root has a single parent

all nodes that are reachable in a tree through a sequence
of maps v→parent[v] are called ancestors of v

all nodes that are reachable in a tree through a sequence
of maps v→child[v] are called descendants of v
5

Tree – basic terms



level or depth of a node is the length of path from the root to
the node. The root thus has depth 0, while its children are on
depth 1.

tree height is the length of the longest path from root to any
leaf
depth
0

height=4 2

4
6

Tree – basic terms



in an ordered tree the children of each node are
arranged with respect to certain order (e.g., by value,
alphabet, …)
3

in a skew tree every node 5
except leaf has a single child; 6
a skew tree with n nodes has 8
height n-1
9

a tree is balanced, if the lengths
of all paths from the root to the A

leaves are equal or differ by at B C D


most 1 E F G H I

J K L
7

Binary tree

a binary tree is a tree in which nodes have at most
degree 2

a binary tree with no nodes is an empty tree or a null
tree. We denote it with NIL.

every node in a binary tree has a left subtree and a right
subtree which can be empty root
left right

if the left subtree is not empty subtree subtree

its root is a left child; if the


right subtree is not empty its
root is a right child
8

Binary tree


in a full binary tree each node has 0 or 2
children
depth

in a perfect or complete binary 0
tree all inner nodes have two 1
children and all leaves are on the height=3
2
same depth 3


a special case of balanced binary tree is an
aligned binary tree, in which each level,
except perhaps the last one, has maximum
number of nodes
9

Binary tree – properties



the number of nodes on depth i in a complete binary tree
is 2i

the number of nodes on depth i in an arbitrary binary tree
is at most 2i

the number of inner nodes in a complete binary tree of
height h is 2h – 1

the number of inner nodes in an arbitrary binary tree of
height h is at most 2h – 1

a complete binary tree of height h has n = 2h+1 – 1 nodes;
for a given n the tree height is h = log2(n+1) – 1

a (left or right) aligned binary tree has height
h = ⌈log2(n+1) − 1⌉
10

Binary search tree



let the tree nodes be objects with following elements:
– key is a data field of a node
– leftChild and rightChild are pointers to left and right child
(can be NIL)
– parent is a pointer to parent

we access the root of tree T through root[T]

a binary search tree is a binary tree in which all keys are
stored such that for each node x of the tree the following holds:
– if node y is in the left
8
subtree of x, then
key[y] ≤ key[x] 4 12

– if node y is in the right 1 6 10 15


subtree of x, then
key[y] ≥ key[x] 3 5 14 18
11

Binary search tree



inorder tree walk allows printing of keys in an ordered
sequence
● an elegant recursive implementation is INORDER-TREE-
WALK(x), which is called with initial argument x=root
INORDER-TREE-WALK(x)
if x ≠ NIL then
INORDER-TREE-WALK(leftChild[x])
print key[x]
INORDER-TREE-WALK(rightChild[x])

time complexity of procedure is O(n)
12

Binary search tree



the same set of keys can be represented with different
binary trees;the number of different trees with same
n keys is: (2 n)!
C (n)= Catalan numbers
(n+1)!⋅n!

a tree of smaller height is more efficient
1
for some operations 1
3 3
6 3
1 6 4
3 10 10
4 10 6
1 4 11 6 11
11 10
4
11
13

Binary search tree – search


● procedure TREE-SEARCH(x,k) searches for key k in
binary search tree T; search starts in the root, i.e., by
calling TREE-SEARCH(root[T],k)

in each step we compare the key of current node x with k:
– if k = key[x], we found the key and return the pointer to the
current node
– if k < key[x], we repeat the search in the left subtree (if it
doesn't exist, the key is not in the tree and we return NIL)
– if k > key[x], we repeat the search in the right subtree (if it
doesn't exist, the key is not in the tree and we return NIL)

time complexity of procedure is O(h)
14

Binary search tree – search



recursive implementation:
TREE-SEARCH(x,k)
if x = NIL or k = key[x] then
return x % key does not exist or was found
if k < key[x] then
return TREE-SEARCH(leftChild[x],k) % search left subtree
else
return TREE-SEARCH(rightChild[x],k) % search right subtree


iterative implementation:
ITERATIVE-TREE-SEARCH(x,k)
while x ≠ NIL and k ≠ key[x] do
if k < key[x] then
x ← leftChild[x] % move to left subtree
else
x ← rightChild[x] % move to right subtree
return x
15

Binary search tree – search


● example: execute search TREE-SEARCH(1,17)
1
15

2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9
16

Binary search tree – search


● example: execute search TREE-SEARCH(1,17)
1
15
17>15
2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9

Because 1≠NIL and 17>key[1]=15, continue in right


subtree by calling TREE-SEARCH(3,17).
17

Binary search tree – search


● example: execute search TREE-SEARCH(1,17)
1
15

2 3
6 18
17<18
4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9

Because 3≠NIL and 17>key[3]=18, continue in left


subtree by calling TREE-SEARCH(6,17).
18

Binary search tree – search


● example: execute search TREE-SEARCH(1,17)
1
15

2 3
6 18

4 5 6 7
3 7 17 20
17=17
8 9 10
2 4 13

11
9

Because 6≠NIL and 17=key[6]=17, the procedure


returns 6.
19

Binary search tree – search


● example: execute search TREE-SEARCH(1,8)
1
15

2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9
20

Binary search tree – search


● example: execute search TREE-SEARCH(1,8)
1
15
8<15
2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9

Because 1≠NIL and 8<key[1]=15, continue in left


subtree by calling TREE-SEARCH(2,8).
21

Binary search tree – search


● example: execute search TREE-SEARCH(1,8)
1
15

2 3
6 18
8>6
4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9

Because 2≠NIL and 8>key[2]=6, continue in right


subtree by calling TREE-SEARCH(5,8).
22

Binary search tree – search


● example: execute search TREE-SEARCH(1,8)
1
15

2 3
6 18

4 5 6 7
3 7 17 20
8>7
8 9 10
2 4 13

11
9

Because 5≠NIL and 8>key[5]=7, continue in right


subtree by calling TREE-SEARCH(10,8).
23

Binary search tree – search


● example: execute search TREE-SEARCH(1,8)
1
15

2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13
8<13
11
9

Because 10≠NIL and 8<key[10]=13, continue in left


subtree by calling TREE-SEARCH(11,8).
24

Binary search tree – search


● example: execute search TREE-SEARCH(1,8)
1
15

2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13
8<13
11
9

NIL

Because 11≠NIL and 8<key[11]=9, continue in left


subtree by calling TREE-SEARCH(NIL,8).
25

Binary search tree – search


● example: execute search TREE-SEARCH(1,8)
1
15

2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13
8<13
11
9

NIL

Because x=NIL, the procedure return NIL.


26

Binary search tree – search



we are often interested in smallest or largest key stored in
some (sub)tree
● procedure TREE-MINIMUM(x) returns a pointer to
element with the smallest key in a binary search tree with
root x by following the left branch until encountering NIL
TREE-MINIMUM(x) 1
15
while leftChild[x] ≠ NIL do
x ← leftChild[x] 2 3
return x 6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9
27

Binary search tree – search



we are often interested in smallest or largest key stored in
some (sub)tree
● procedure TREE-MAXIMUM(x) returns a pointer to
element with the largest key in a binary search tree with
root x by following the right branch until encountering NIL

time complexity of procedures is O(h)
TREE-MAXIMUM(x) 1
15
while rightChild[x] ≠ NIL do
x ← rightChild[x] 2 3
return x 6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9
28

Binary search tree – search



we are also often interested in finding a successor or
predecessor of node x in a (sub)tree using procedures
TREE-SUCCESSOR(x) and TREE-PREDECESSOR(x)

a successor of node x is a node with smallest larger key
than key[x]; a predecessor of node x is a node with largest
smaller key than key[x]

example: 1
15
– predecessor of node 2
(key value 6) is node 9 2
6 18
3

(key value 4) 4 5 6 7
3 7 17 20
– successor of node 10 8 9 10

(key value 13) is node 1 2 4 13

(key value 15) 11


9
29

Binary search tree – search



finding the successor splits into two options*:
– if the right subtree of node x is nonempty, then the successor of
x is the leftmost node in the right subtree
– if the right subtree of node x is empty, then the successor of x is
the first node into which we step from the left subtree when
backtracking from x towards the root, or NIL if such node does
not exist
TREE-SUCCESSOR(x)
if rightChild[x] ≠ NIL then
return TREE-MINIMUM(rightChild[X])
y ← parent[x]
while y ≠ NIL and x = rightChild[y] do
x ← y
y ← parent[y]
return y
30

Binary search tree – search



finding the predecessors is symmetrically analogue
TREE-PREDECESSOR(x)
if leftChild[x] ≠ NIL then
return TREE-MAXIMUM(leftChild[X])
y ← parent[x]
while y ≠ NIL and x = leftChild[y] do
x ← y
y ← parent[y]
return y

time complexity of both procedures is O(h)
31

Binary search tree – search



example: execute call TREE-SUCCESSOR(1)
– because node 1 has non-empty right subtree (the right
child is node 3), we call TREE-MINIMUM(3) which returns
pointer to node x=6 with key 17

1
15

2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9
32

Binary search tree – search


● example: execute call TREE-SUCCESSOR(7)
– because node 7 has empty right subtree, we backtrack
towards the root
– while backtracking we never return from the left branch,
therefore the loop terminates when we reach NIL, so we
return NIL 1
15

2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9
33

Binary search tree – search


● example: execute call TREE-SUCCESSOR(10)
– because node 10 has empty right subtree, we backtrack
towards the root
– while backtracking from node x=2 into node y=1 we return
from the left branch, therefore the loop terminates and we
return the pointer to node y=1 with key 15
1
15

2 3
6 18

4 5 6 7
3 7 17 20

8 9 10
2 4 13

11
9
34

Binary search tree – insertion


TREE-INSERT(T,k)

inserts a new node z with create new node z
key key[z]=k into a binary key[z] ← k
leftChild[z] ← NIL
search tree T rightChild[z] ← NIL

the inserted node becomes y ← NIL
x ← root[T]
a new leaf of the tree while x ≠ NIL do

the procedure first finds the y ← x
if k < key[x] then
correct node position by x ← leftChild[x]
moving from the root else
x ← rightChild[x]
towards leaves and then parent[z] ← y
connecting the new leaf with if y = NIL then
root[T] ← z
its parent else if k < key[y] then

the time complexity of leftChild[y] ← z
else
procedure is O(h) rightChild[y] ← z
35

Binary search tree – insertion


example: insert key 16 into existing tree T
1
15 1
15
2 3
26 18 3
6 19
4 5 6 7
3 7 17 20
4 5 6 7
3 7 17
8 20
13
8
18
36

Binary search tree – insertion


example: insert key 16 into existing tree T
1
15 1
15
2 3
26 18 3
6 19
4 5 6 7
3 7 17 20
4 5 6 7
3 7 17
8 20
13
8
18
37

Binary search tree – insertion


example: insert key 16 into existing tree T
1
15 1
15
2 3
26 18 3
6 19
4 5 6 7
3 7 17 20
4 5 6 7
3 7 17
8 20
13
z 8
16 18
38

Binary search tree – deletion

● procedure TREE-DELETE(T,z) removes node z


from tree T TREE-DELETE(T,z)
if leftChild[z]=NIL or rightChild[z]=NIL then

the time complexity else
y ← z

of the procedure is y ← TREE-SUCCESSOR(z)


if leftChild[z] ≠ NIL then
O(h) x ← leftChild[y]
else
x ← rightChild[y]
if x ≠ NIL then
parent[x] ← parent[y]
if parent[y] = NIL then
root[T] ← x
else if y = leftChild[parent[y]] then
leftChild[parent[y]] ← x
else
rightChild[parent[y]] ← x
if y ≠ z then
key[z] ← key[y]
destroy node y
39

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z is a leaf we only set a pointer to child z at its parent to
NIL

15 15

6 19 6 19

z
3 7 17 20 3 17 20

16 18 16 18
40

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z has a single child, we make a bypass connection
between parent of z and child of z

15 15

z
6 18 6 22

3 7 22 3 7 20

20
41

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z has two children, we move to z's position the smallest
(i.e., the leftmost)* element from the right subtree or the
largest (i.e., the rightmost) element from the left subtree
– move = copy + delete
15
z
6 18

3 7 17 20

2 4 13

9
42

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z has two children, we move to z's position the smallest
(i.e., the leftmost)* element from the right subtree or the
largest (i.e., the rightmost) element from the left subtree
– move = copy + delete
15
z
4 18

3 7 17 20

2 4 13

9
43

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z has two children, we move to z's position the smallest
(i.e., the leftmost)* element from the right subtree or the
largest (i.e., the rightmost) element from the left subtree
– move = copy + delete
15
z
4 18

3 7 17 20

2 13

9
44

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z has two children, we move to z's position the smallest
(i.e., the leftmost) element from the right subtree or the
largest (i.e., the rightmost)* element from the left subtree
– move = copy + delete
15
z
6 18

3 7 17 20

2 4 13

9
45

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z has two children, we move to z's position the smallest
(i.e., the leftmost) element from the right subtree or the
largest (i.e., the rightmost)* element from the left subtree
– move = copy + delete
15
z
7 18

3 7 17 20

2 4 13

9
46

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z has two children, we move to z's position the smallest
(i.e., the leftmost) element from the right subtree or the
largest (i.e., the rightmost)* element from the left subtree
– move = copy + delete
15
z
7 18

3 7 17 20

2 4 13

9
47

Binary search tree – deletion



when deleting node z we distinguish three scenarios:
– if z has two children, we move to z's position the smallest
(i.e., the leftmost) element from the right subtree or the
largest (i.e., the rightmost)* element from the left subtree
– move = copy + delete
15
z
7 18

3 13 17 20

2 4 9

You might also like