树的实例:模拟文件系统

class Node:def __init__(self, name, type='dir'):self.name = nameself.type = type #'dir' or 'file'self.children = []self.parent = Nonedef __repr__(self):return self.namen = Node('Hello')
m = Node('world')
n.children.append(m)
m.parent = nclass FileSystemTree:def __init__(self):self.root = Node("/")self.now = self.rootdef mkdir(self, name): #创建文件夹,name以/结尾if name[-1] == '/':name += '/'node = Node(name)self.now.children.append(node)node.parent = self.nowdef ls(self): #列出目录内容return self.now.childrendef cd(self, name):if name[-1] == '/':name += '/'if name == '../':self.now = self.now.parentreturnfor child in self.now.children:if child.name = name:self.now = childreturnraise ValueError('invalid dir')       

二叉树

  • 二叉树的链式存储:将二叉树的节点定义为一个对象,节点之间通过类似链表的链接方式来连接

代码:

def BiTreeNode:def __init__(self, data):self.data = dataself.lchild = None #左孩子self.rchild = None #右孩子

二叉树的遍历

  • 前序遍历:EACBDGF
  • 中序遍历:ABCDEGF
  • 后续遍历:BDCAFGE
  • 层次遍历:EAGCFBD

代码:

def pre_order(root): #前序if root:print(root.data, end=',')pre_order(root.lchild)pre_order(root.rchild)def in_order(root): #中序if root:in_order(root.lchild)print(root.data, end=',')in_order(root.rchild)def post_order(root): #后序if root:post_order(root.lchild)post_order(root.rchild)print(root.data, end=',')from collections import deque
def level_order: #层次queue = deque()queue.append(root):while len(queue) > 0: #只要队不空node = queue.popleft()print(node.data, end=',')if node.lchild:queue.append(node.lchild)if node.rchild:queue.append(node.rchild)

二叉搜索树

  • 二叉搜索树是一颗二叉树且满足性质:设x是二叉树的一个节点。如果y是x左子树的一个节点,那么y.key≤x.key;如果y是x右子树的一个节点,那么y.key≥x.key
  • 二叉搜索树的操作:查询、插入、删除
  • 对于二叉搜索树来说,中序遍历一定是有序的
  • 删除操作:
    • 如果节点是叶子节点,直接删除
    • 如果节点只有一个孩子,将此节点的父亲与孩子连接,然后删除该节点
    • 如果节点有两个孩子,将其右子树的最小节点(该节点最多有一个右孩子)删除,并替换当前节点

代码:

def BiTreeNode:def __init__(self, data):self.data = dataself.lchild = None #左孩子self.rchild = None #右孩子self.parent = Noneclass BST: #二叉搜索树def __init__(self, li=None):self.root = Noneif li:for val inli:self.insert_no_rec(val)def query(self,val): #递归实现查询if not node:return Noneif node.data < val:return self.query(node.rchild, val)elif node.data > val:return self.query(node.lchild, val)else:return Nonedef query_no_rec(self, val): #非递归实现查询p = self.rootwhile p:if p.data < val:p = p.rchildelif p.data > val:p = p.lchildelse:return preturn Nonedef insert(self, node, val): #递归实现插入if not node:node = BiTreeNode(val)elif val < node.data:node.lchild = self.insert(node.lchild, val)node.lchild.parent = nodeelif val > node.data:node.rchild = self.insert(node.rchild, val)node.rchild.parent = nodereturn nodedef insert_no_rec(self, val): #非递归实现插入p = self.rootif not p: #空树self.root = BiTreeNode(val)returnwhile True:if val < p.data:if p.lchild:p = p.lchildelse:p.lchild = BiTreeNode(val)p.lchild.parent = preturnelif val > p.data:if p.rchild:p = p.rchildelse:p.rchild = BiTreeNode(val)p.rchild.parent = preturnelse:returndef __remove_node_1(self, node): #情况1:node是叶子节点if not node.parent:self.root = Noneif node == node.parent.lchild: #如果node是它父亲的左孩子node.parent.lchild = Noneelse: #如果node是右父亲的左孩子node.parent.rchild = Nonedef __remove_node_21(self, node): #情况2.1:node只有一个左孩子if not node.parent: #如果是根节点self.root = node.lchildnode.lchild.parent = Noneelif node == node.parent.lchild:node.parent.lchild = node.lchildnode.lchild.parent = node.parentelse:node.parent.rchild = node.lchildnode.lchild.parent = node.parentdef __remove_node_22(self, node): #情况2.1:node只有一个右孩子if not node.parent: #如果是根节点self.root = node.rchildnode.rchild.parent = Noneelif node == node.parent.lchild:node.parent.lchild = node.rchildnode.rchild.parent = node.parentelse:node.parent.rchild = node.rchildnode.rchild.parent = node.parentdef delete(self, val):if self.root: #不是空树node = self.query_no_rec(val)if not node: #不存在return Falseif not node.lchild and not node.rchild: #没有左孩子和右孩子self.__remove_node_1(node)elif not node.rchild: #只有左孩子self.__remove_node_21(node)elif not node.lchild: #只有右孩子self.__remove_node_22(node)else: #两个孩子都有min_node = node.rchild #找右子树最小节点while min_node.lchild:min_node = min_node.lchildnode.data = min_node.data#删除min_nodeif min_node.rchild:self.__remove_node_22(min_node)else:self.__remove_node_1(min_node)

二叉搜索树的效率

  • 平均情况下,二叉搜索树进行搜索的时间复杂度为O(logn)
  • 最坏情况下,二叉搜索树可能非常偏斜
  • 解决方案
    • 随机化插入
    • AVL树

二叉搜索树扩展应用——B树

  • B-Tree是一棵自平衡的多路搜索树。常用于数据库的索引。

L13:数据结构-5(树和二叉树)相关推荐

  1. 【数据结构】 树与二叉树的基本概念、结构特点及性质

    前言:本章内容主要是数据结构中树与二叉树的基本概念.结构特点及性质的引入. 文章目录 树的概念 树的特点: 树的常用术语: 树的表示: 代码创建: 树在实际中的应用: 二叉树的概念 特殊的二叉树 满二 ...

  2. 数据结构之树与二叉树

    数据结构之树与二叉树 1.树的概念及结构 1.1.什么是树? 树是一种非线性的数据结构,它是由n(n>=0)个有限结点组成一个具有层次关系的集合.树是递归定义的.之所以把它叫做树是因为它看起来像 ...

  3. 【图解数据结构】树和二叉树全面总结(上)

    目录 一.前言 二.树的概念和定义 三.二叉树 1.基本概念 2.基本形态 3.性质 4.满二叉树 5.完全二叉树 四.存储结构 1.顺序存储 2.二叉链表 3.三叉链表 一.前言 学习目标:理解树和 ...

  4. 数据结构-王道-树和二叉树

    [top] 树和二叉树 树:是\(N(N\geq0)\)个结点的有限集合,\(N=0\)时,称为空树,这是一种特殊情况.在任意一棵非空树中应满足: 有且仅有一个特定的称为根的结点. 当\(N>1 ...

  5. 天勤数据结构:树与二叉树(图解二叉树的三种遍历方式执行流程,超详细)

    数据结构(第六章) 树与二叉树 1. 树与二叉树的相互转换 2. 森林与二叉树的相互转换 3. 二叉树的遍历 3.1 层序遍历(广度优先遍历) 2. 深度优先遍历 3. 树转化为二叉树的遍历 将一颗 ...

  6. 数据结构 5-0 树与二叉树总结

    前言 数据结构复习过程中最先遭遇的磕碰,这一章内容及其多,而且可以考得很难,不仅是代码题,填空题有些也很有难度.主要是四部分内容:树的基本概念.二叉树.树与森林.树的应用.题目以选择题为主,因为代码题 ...

  7. 数据结构:树与二叉树(一) 树的基本知识

    这篇文章给大家简单讲一下树. 1.树逻辑结构 (1)树(Tree)是一个非空的有限元素的集合,元素之间有如下关系:有且仅有一个特殊元素,它没有前驱(称为树根Root),其余元素都有且仅有一个前驱元素, ...

  8. 《王道》数据结构之树和二叉树(五)

    数据结构入门之树和二叉树(五) 大纲 一.树的概念和性质 1.1 树的概念 1.1.1 树的定义 1.1.2 结点分类与结点间关系 1.1.3 树的其他相关概念 1.2 (非空)树的性质 1.3 树的 ...

  9. 【C语言 - 数据结构】树、二叉树(上篇)

    树是计算机算法最重要的非线性结构.因为树能很好地描述结构的分支关系和层次特性,所以在计算机科学和计算机应用领域有着广泛的应用.这篇文章我就带大家一起了解一下树.二叉树这种结构,下篇文章会重点向大家介绍 ...

  10. 数据结构(树与二叉树)

    5.1.1树和二叉树的定义 树:是n(n>=0)个结点的有限集,或为空树(n==0),或为非空树 非空树满足:1.有且仅有一个称之为根的结点                           ...

最新文章

  1. hadoop伪分布式安装
  2. log4j.properties 详解与配置步骤总结
  3. 正在CPU上运行的进程_进程的概念,系统资源分配的单元
  4. 白领丽人:这六行盛产“钻石王老五”
  5. php文件安全实现方法,php安全下载大文件的实现代码
  6. 02-HTTP的请求方法以及响应状态码
  7. xLite连接asterisk提示sip408错误
  8. python实现isodd函数、参数为整数、如果整数为奇数_python 程序练习题
  9. 李佳琦抢了薇娅的流量
  10. k8s核心技术-Service概述_Service如何实现负载均衡_提供虚拟IP_以及Po的IP注册和发现---K8S_Google工作笔记0031
  11. Win10/Server2016镜像集成离线补丁
  12. MySQL外键约束详解
  13. 轻松学习java可重入锁(ReentrantLock)的实现原理
  14. 记事狗微博php,记事狗微博系统_366rtc 源码采用php实现 - 下载 - 搜珍网
  15. [压位DP]Hdu 6149——Valley Numer II
  16. java隐藏字符_Java原生隐藏字符-工具类
  17. c语言 北京时间转换utc时间_UTC时间转换成北京时间C语言函数代码
  18. 一文读懂SIMD指令集 目前最全SSE/AVX介绍
  19. 可道云kodexplorer搭建私有云后的配置优化
  20. SMETA验厂辅导,提出过不合规项的所有部分,应对以下内容有清楚的解释

热门文章

  1. 光盘驱动器托盘被卡住属于计算机硬故障中的,光驱托盘不会打开?打开卡住CD DVD驱动器托盘的提示 | MOS86...
  2. 诺贝尔经济学奖与数学
  3. html导航栏分割线如何,网页导航栏用图片做的分割线,第一个分割线怎么取消...
  4. 《王二丫的甜品店》用户隐私政策
  5. 二分图匹配-匈牙利算法, 最小路径覆盖
  6. Android 常用框架大全
  7. execute和submit的区别
  8. GSOAP 在一个客户端内调用多个服务出现的问题解决
  9. nmap 扫描 STATE 显示closed
  10. AndroidStudio