python實現二叉樹的添加,深度遍歷和廣度遍歷

樹的常用術語

1.節點的度: 一個節點含有的子節點的個數
2.樹的度: 樹結構中最大的節點的度, 最大的分支節點個數
3.葉節點: 度爲零的節點, 沒有子節點的末端節點
4.節點的層次: 從根開始, 根是第一層, 一次往下數
5.樹的深度: 樹中節點最大層次

二叉樹的概念

  • 二叉樹是一種有序樹,每個節點最多含有兩個子節點
  • 二叉樹的分類:
    完全二叉樹: 除了最下層,每一層的度數都最大
    滿二叉樹: 所有子節點都達到最滿
    平衡二叉樹: 任何節點的兩棵子樹的高度差不大於1
    二叉排列數 : 分支上的數據有一定的順序

二叉樹的遍歷

把二叉樹中的所有節點都訪問一遍

  • 深度優先: 沿着樹的深度遍歷樹的節點, 有三種方法:
    - 先序遍歷 根節點->左子樹->右子樹
    - 中序遍歷 左子樹->根節點->右子樹
    - 後續遍歷 左子樹->右子樹->根節點
  • 廣度優先: 從樹的root根開始, 從上到下從左到右, 從水平的寬度上來遍歷

python3 實現樹的添加, 三種深度遍歷和廣度遍歷

# 二叉樹的用法


class Node(object):
    # 節點類
    def __init__(self, elem):
        self.elem = elem
        self.lchild = None
        self.rchild = None


class Tree(object):
    # 樹類
    def __init__(self):
        # 根節點是root
        self.root = None

    def add(self, elem):
        # 向樹中添加節點
        # 先創建一個節點對象
        node = Node(elem)
        # 如果樹是空的, 那麼 root節點
        if self.root is None:
            self.root = node
            return

        # todo 直接放到列表中就可以, 用append添加的方式不行
        queue = [self.root]
        # 隊列的方式, 遍歷元素放入隊列中
        # queue = queue.append(self.root)
        # 退出循環的條件, 隊列是空的
        while queue:
            # 彈出隊列的第一個元素
            cur_node = queue.pop(0)
            # 如果節點的左孩子是空的
            if cur_node.lchild is None:
                # 把元素放在該節點
                cur_node.lchild = node
                return
            # 節點的右孩子是空的
            elif cur_node.rchild is None:
                # 把元素放在該節點
                cur_node.rchild = node
                return
            else:
                # 左右海子都不爲空, 添加到隊列中繼續判斷
                queue.append(cur_node.lchild)
                # queue.append(cur_node.rchild)

    def breadth_travel(self):
        """利用隊列實現樹的層次遍歷"""

        if self.root == None:
            return
        queue = []
        queue.append(self.root)

        while queue:
            node = queue.pop(0)
            print(node.elem)
            if node.lchild != None:
                queue.append(node.lchild)
            if node.rchild != None:
                queue.append(node.rchild)

    # 先序遍歷 根 左 右
    def preorder(self, node):
        if node is None:
            return
        # 打印根節點, 
        print(node.elem)
        # 遞歸找出每一個節點, 左節點遞歸
        self.preorder(node.lchild)
        # 遞歸找出每一個節點,右節點遞歸
        self.preorder(node.rchild)

    # 中序遍歷 左 根 右
    def inorder(self, node):
        if node is None:
            return
        self.inorder(node.lchild)
        print(node.elem)
        self.inorder(node.rchild)

    # 後序遍歷 左 右 根
    def backorder(self, node):
        if node is None:
            self.backorder(node.rchild)
            self.backorder(node.lchild)
            print(node.elem)

if __name__ == '__main__':
    tree = Tree()
    tree.add(9)
    tree.add(1)
    tree.add(2)
    tree.add(3)
    tree.add(5)
    tree.breadth_travel()
    print("----------")
    # 將根節點對象傳遞過去
    tree.inorder(tree.root)
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章