Pretty Print a Binary Tree in Python

A Binary Tree is a finite set of elements that is either empty or is partitioned into three disjoint subsets. The first subset contains a single element called root. The other two subsets are themselves binary trees and called as left and right subtrees of original tree. Each element of a binary tree is called a node of the tree.

Consider this Binary tree

Binary tree

Here, 10 is the root node, node 2 is the left child of the root node and node 21 is the right child of the root node and similarly for the rest of the tree.

Visualizing a binary tree can help in understanding its structure and the relationships between its nodes. Let’s write a Python script to pretty print a binary tree in Python using ASCII characters to represent the tree structure.

Printing the Binary Tree

To print the binary tree, we need a recursive function that will traverse the tree and print each node in a structured manner. We’ll use ASCII characters to draw the tree branches:

  • to represent a vertical branch
  • └── to represent a left child
  • ┌── to represent a right child
Pseudocode

The idea here is to do a Depth First Traversal of the Binary tree and determine each node’s position in the tree.

Depth-First Traversal
1. First recursively traverse the right subtree,
2. Then process the current node,
3. And finally traverse the left subtree.

Processing the node
1. Use a prefix parameter to keeps track of the current indentation level and structure.
2. Use is_left parameter to track whether the current node is a left child or right child.
3. The current node’s value is printed with the appropriate prefix. If it’s a left child, the prefix includes └──; if it’s a right child, the prefix includes ┌──.

This ensures that the tree is printed from top to bottom and right to left.

Depth First Traversal is discussed in detail in this post – DFS (Depth-First Search) in Binary Trees and Graphs

Code Implementation
# Class to represent a Tree node
class TreeNode:
    def __init__(self, value):
        self.value = value
        self.left = None
        self.right = None


def print_tree(root, prefix="", is_left=True):
    if root is not None:
        print_tree(root.right, prefix + ("│   " if is_left else "    "), False)
        print(prefix + ("└── " if is_left else "┌── ") + str(root.value))
        print_tree(root.left, prefix + ("    " if is_left else "│   "), True)


# Example Usage
root = TreeNode(10)
root.left = TreeNode(2)
root.right = TreeNode(21)
root.right.left = TreeNode(15)
root.right.right = TreeNode(31)

print_tree(root)

Output

│       ┌── 31
│ ┌── 21
│ │ └── 15
└── 10
└── 2

Time complexity: O(N), print_tree function visits each node exactly once, performing constant-time operations for each node.
Auxiliary Space: O(N), primary space usage comes from the recursive call stack, which can grow to a depth of N in the worst case (skewed tree).

The print_tree function is efficient in terms of both time and space complexity for most practical purposes. This method is particularly useful for debugging and understanding the structure of Binary Trees.

Leave a Reply

Your email address will not be published. Required fields are marked *