node - an item or piece of data that makes the data structure
Root - the first node at the top of a tree
Left/Right Child - node to the left or right of it’s parent node
Edge - The link between a parent and child node
Leaf - A node that does not have any children
Height - The number of edges from the root node to the lowest node
While trees can have any number of children per node, binary trees can only have two- a right and a left child. Nodes can be added to a tree wherever there is space, there is no specific sorting order.
It doesn’t matter how a new node gets added to a binary tree. But for example you can fill child spots from the top down.
For time:
A binary tree isn’t really organized, assuming a tree has n
node, you might have to look at n
number of items in order to find that one.
For space using breadth-first:
w
being the largest width of the tree.
Perfect Binary Tree?
When every node that isn’t a leaf has two children, therefor- the maximum width for a perfect tree is 2^(h-1)
. h
=height, height being calculated as log n
, where n
is the number of nodes.
A BST does have some structure. The nodes are organized where values that are less than the root/parent become the left child, while those values which are greater are assigned as the right child
Compare the node you are looking for against the root/root of a sub-tree to determine if the value is greater than or less than. If less, traverse left, if greater, traverse right.
For time:
in a perfect tree. the h = log(n)
For space:
because we are not allocating additional space
Three methods for depth first traversal:
root>>left>>right
ex: A,B,D,E,C,F
The root must be looked at first and output it’s value will be added to the call stack each time preOrder is called.
root.left/root.right
return null, you know you are at the leaf and the execution will end.algorithm for pre-order
ALGORITHM preOrder(root)
// INPUT <-- root node
// OUTPUT <-- pre-order output of tree node's values
OUTPUT <-- root.value
if root.left is not Null
preOrder(root.left)
if root.right is not NULL
preOrder(root.right)
OTHER ALGORITHMS FOR DEPTH FIRST, DIFFERENCE IS WHEN YOU ARE LOOKING AT ROOT NODE DURING TRAVERSAL
algorithm for in-order
ALGORITHM inOrder(root)
// INPUT <-- root node
// OUTPUT <-- in-order output of tree node's values
if root.left is not NULL
inOrder(root.left)
OUTPUT <-- root.value
if root.right is not NULL
inOrder(root.right)
algorithm for post-order
ALGORITHM postOrder(root)
// INPUT <-- root node
// OUTPUT <-- post-order output of tree node's values
if root.left is not NULL
postOrder(root.left)
if root.right is not NULL
postOrder(root.right)
OUTPUT <-- root.value
root>>left & right
ex: A,B,C,D,E,F
Different from depth-first in that it uses a queue instead of a (call) stack in order to traverse the width&breadth of tree.
enqueue
it’s left (first) and right (second) children.algorithm for breadth-first
ALGORITHM breadthFirst(root)
// INPUT <-- root node
// OUTPUT <-- front node of queue to console
Queue breadth <-- new Queue()
breadth.enqueue(root)
while breadth.peek()
node front = breadth.dequeue()
OUTPUT <-- front.value
if front.left is not NULL
breadth.enqueue(front.left)
if front.right is not NULL
breadth.enqueue(front.right)