Data Structures Binary Trees: Phil Tayco Slide Version 1.1 Apr. 2, 2018
Data Structures Binary Trees: Phil Tayco Slide Version 1.1 Apr. 2, 2018
Binary Trees
Phil Tayco
Slide version 1.1
Apr. 2, 2018
Binary Trees
Back to Linked Lists
10
Binary Trees
Next, insert 20. 20 is greater than 10 and its right
pointer is null, so we add it there
root
10
20
Binary Trees
Next, insert 5. 5 is less than 10 (we always start at
root) and its left pointer is null, so we add it there
root
10
5 20
Binary Trees
Now insert 15. 15 is greater than 10 so we go right.
20 is there so we check again and find 15 less
than it. 20’s left pointer is null so we add 15
there
root
10
5 20
15
Binary Trees
One more. Insert 25. Starting at root, 25 is greater
than 10 and then greater than 20 so we add it to
the right of 20
root
10
5 20
15 25
Binary Trees
public class BinaryTree
{
private Node root;
public BinaryTree()
{
root = null;
}
Binary Trees
public void insert(int n)
{
Node current = root;
Node newNode = new Node();
newNode.data = n;
newNode.left = null;
newNode.right = null;
if (root == null)
root = newNode;
Binary Trees
else
while(true)
if (newNode.data > current.data)
if (current.right == null)
{
current.right = newNode;
break;
}
else
current = current.right;
else
if (current.left == null)
{
current.left = newNode;
break;
}
else
current = current.left;
}
Binary Trees
Code analysis
• Each node “visited” effectively cuts off the other half of the list
• If the values being added have a random distribution of values,
the performance is like a binary search and is thus, O(log n)
• Note that there is a dependency on the manner in which Nodes
are inserted
– If the root is too small or too large, subsequent levels will be on one
side of it
– If this pattern continues (such as inserting numbers in numeric order),
the tree degrades into a linked list
– Efficiency in such “unbalanced” trees degrades to O(n) for all functions
• There are ways to counter unbalancing in more advanced tree
structures which we’ll look at later
• As you can imagine, the other 3 major functions will follow a
similar algorithm and efficiency. Let’s look at “search” next
Binary Trees
Binary search enabled
root
10
5 20
15 25
Binary Trees
“Parent” nodes have either left and/or right pointers
of it pointing to existing nodes. 10 is the parent
of 5 and 20. 20 is the parent of 15 and 25
root
10
5 20
15 25
Binary Trees
“Child” nodes are nodes with a parent. 5 is a child
of 10 and so is 20. 15 and 25 are children of 20.
These nodes are also “siblings” to each other
because they share the same parent
root
10
5 20
15 25
Binary Trees
“Leaf” nodes are nodes with no
children. 5, 15 and 25 are such
leaves
root
10
5 20
15 25
Binary Trees
Each “generation” of nodes is called a “level”. 10 is
at level 0, 5 and 20 are at level 1 and 15 and 25
at level 2. The number of levels a tree has is
called its “height”
root
10
5 20
15 25
Binary Trees
Traversing a tree is similar to traversing a linked list
in that you follow the node pointers to get where
you want. In a tree, such traversals are called a
“path”
root
10
5 20
15 25
root
10
5 20
root
10
5 20
15 25
Binary Trees
Because 25 has no children, its parent node’s
“right” pointer can simply point to null
root
10
5 20
15
Binary Trees
Easy enough. Next situation is removing a node
with 1 child. That would be 10 and 20 in the tree
below. Let’s delete 20
root
10
5 20
15
Binary Trees
Now we have to make sure 20’s parent points to
the correct child of 20. More specifically, since 20
is on the “right” of 10, 10’s “right” pointer must
point to the correct child of 20
root
10
5 20
15
Binary Trees
It turns out this is not terribly difficult because 20 (in this
situation) only has one child to choose from. Since that
child is on 20’s “left”, we make 10’s “right” point to 20’s
“left” which is 15
root
10
5 15
Note that the order of the entire tree is maintained even
though 15 was on the “left” of 20 (this was because 15
was first added by going to the “right” of 10 during insert)
Binary Trees
What if the one child of 20 was a large subtree?
Because of the way the pointers are set up and
how insert works, the overall tree order still
remains intact. For example:
root
10
5 20
15
12
11 14
Binary Trees
If we remove 20, 20 still only has 1 direct child, so
when we assign 20’s parent’s right child to 20’s
left child, that entire subtree becomes 10’s “right”
child and the order is still intact
root
10
5 15
12
11 14
Binary Trees
Situations 1 and 2 addressed
10
5 20
15
12
11 14
Binary Trees
If we remove 12, note that either 11 and 14 can
take its place and the structure order will remain
intact
root
10
5 20
15
11 14
Binary Trees
15 can take 11 as its left child and 14 would then
become the right child of 11
root
10
5 20
15
11
14
Binary Trees
Similarly, 14 could also be the left child of 15 and
11 would then have to become 14’s left child
root
10
5 20
15
14
11
Binary Trees
Situation 3
10
50
5 20 75
15
12
11 14
Binary Trees
If we replaced it with node 5, the structure is intact
implying that if one of the child nodes is a leaf, it
can replace the node being removed
root
30
5
50
20 75
15
12
11 14
Binary Trees
We could not do the same with 20. Notice in this
example that 20 already has a left child and 10
had one as 5. If 20 takes its place, where does 5
go?
root
30
50
5 20 75
15
12
11 14
Binary Trees
Situation 3
50
5 20 75
15
12
11 14
Binary Trees
14 would not work though because subtree 12
should not be on the “right” of 14
root
30
14
50
5 20 75
15
12
11
Binary Trees
However, 11 works and works very well!
root
30
11
50
5 20 75
15
12
14
Binary Trees
Situation 3 – almost there!
root
30
50
5 20 75
15
12
14
Binary Trees
Replacing 11 with 14 is a problem because 12 is on
the “right” of 14 (it’s the same issue as before
when selecting 14 to replace 10)
root
30
14
50
5 20 75
15
12
Binary Trees
This rules out “always” selecting a leaf node. What
do we do now? First, identify which node in the
subtree should replace 11…
root
30
50
5 20 75
15
12
14
Binary Trees
11 was good to replace 10 because it was the
closest value on the right of it. If we did the same
thing here to replace 11, 12 would be the winner
root
30
12
50
5 20 75
15
14
Binary Trees
But 12 was not a leaf, so what do we do with its
children? It turns out that 12 will only have 1
child and it will be on the right (if it had one on
the left, that child would be better to use as a
root
replacement node!)
30
12
50
5 20 75
15
14
Binary Trees
Note also that 12’s parent will always be its left
child. Thus, the parent left child takes the right
child (and thus, subtree) of the replacing node.
Order is intact!
root
30
12
50
5 20 75
15
14
Binary Trees
The Situation 3 algorithm
• It may seem like a lot of checks, but the code follows the
logic effectively
• First check if the tree is empty (as always) – we’re done if
it is
• Search the tree (using the same search algorithm) for the
node to remove keeping track of not only the parent and
current nodes, but whether the current node is on the left
or right of the parent
• If current ends up as null, the node to remove is not found
and we’re done
• At this point, the node is found and we handle the 3
situations as previously discussed
• Let’s look at the code to see this all in action
Binary Trees
public boolean remove(int n)
{
// Check empty tree
if (root == null)
return false;
remove(oldValue);
insert(newValue);
return true;
}
Binary Trees
Efficiency
root
10
5 15
Binary Trees
If we want to show this tree in sorted order, 10
would not be the first number. From looking at it,
we know we want to display 5 first. However,
how do we state this in logical coding terms?
root
10
5 15
Binary Trees
One way to state it is, “if there is a node to the left,
display the node’s value”. This is then followed
by, “then show my value and then if there is a
node to the right, show its value”
root
10
5 15
Binary Trees
However, trees are not always 2 levels. That logic is
incomplete starting at node 10
root
10
5 15
1 8 12 18
Binary Trees
If we look at the subtree 1-5-8, that does fit our
logic of display left node, then current, then right
root
10
5 15
1 8 12 18
Binary Trees
From the perspective of node 10, we can then
modify our logic to not say “display the node to
the left (or right)”, but “display the subtree to the
left (or right)”
root
10
5 15
1 8 12 18
Binary Trees
Back to recursion!
10 5 1 8 15 12 18
root
10
5 15
1 8 5 12 18 15 10
root
10
5 15
1 8 12 18
Binary Trees
Traversals
root
5 +