要实现二叉树结构的Python实现:
- 首先定义树的抽象基类,以通过继承该基类生成更多的具体类。
- 定义二叉树的抽象基类
- 定义链式二叉树
定义树的抽象基类
通过定义树的抽象基类,支持如下方法:
方法 | 解释 |
---|---|
p.element() | 返回位置p的元素 |
T.root() | 返回树的根节点位置 |
T.is_root( p ) | 判断p是否为根节点 |
T.parent( p ) | 返回p的父节点位置 |
T.children( p ) | 返回p节点的孩子节点位置 |
T.num_children( p ) | 生成p节点孩子节点的迭代器 |
T.is_leaf( p ) | 判断p节点是否为叶节点 |
T.is_empty() | 判断树是否是空树 |
T.positions() | 用来迭代生成树的所有节点即遍历方法 |
len(T) | 返回树所包含的元素数量 |
iter(T) | 迭代生成储存在树中的所有元素 |
T.height(p ) | 返回p节点的高度 |
T.depth( p) | 返回p节点的深度 |
class Tree:
'''树结构的抽象基类'''
#----------------返回节点位置的基类---------------
class Position:
def element(self):
"""Return the element stored at this Position"""
raise NotImplementedError("Must be implemente the subclass")
def __eq__(self, other):
"""Return True or False"""
raise NotImplementedError("Must be implemente the subclass")
def __ne__(self, other):
"""Return True or False"""
return not(self==other)
#--------------------抽象方法------------------------
def root(self):
"""返回树根节点的位置,如果为空树返回None"""
raise NotImplementedError("Must be implemente the subclass")
def parent(self,p):
"""返回节点p的父节点,若为根节点返回None"""
raise NotImplementedError("Must be implemente the subclass")
def children(self,p):
raise NotImplementedError("Must be implemente the subclass")
def num_children(self,p):
"""返回p节点的孩子节点的迭代位置"""
raise NotImplementedError("Must be implemente the subclass")
def __len__(self):
"""返回树种所有节点的个数"""
raise NotImplementedError("Must be implemente the subclass")
#------------------------抽象类的一些具体方法-------------------------------
def is_root(self,p):
"""若是根节点返回True"""
return self.root() == p
def is_lesf(self,p):
return self.num_children(p)==0
def is_empty(self):
return len(self)==0
def depth(self,p):
"""返回p节点的深度,采用迭代的方法 根节点深度为0 时间复杂度O(dp+1)"""
if self.is_root(p):
return 0
else:
return 1 + self.depth(self.parent(p))
def _higth2(self):
if self.is_lesf(p):
return 0
else:
return 1 + max(self._higth2(c) for c in self.children(p))
def hight(self,p=None):
if p is None:
p=self.root()
return self._higth2(p)
定义二叉树的抽象基类
定义二叉树的抽象基类,在继承树的抽象基类的基础上,加入left
、right
和slibing
方法,并重写了children
方法。
class BinaryTree(Tree):
""" 二叉树的抽象基类 """
#----------------其他的抽象方法--------------------
def left(self,p):
raise NotImplementedError("Must be implemente the subclass")
def right(self,p):
raise NotImplementedError("Must be implemente the subclass")
def slibling(self,p):
"""返回p节点的兄弟节点的位置"""
parent=self.parent(p)
if parent is None:
return None
else:
if p==self.left(parent):
return self.right(parent)
else:
return self.left(parent)
def children(self,p):
if self.left(p) is not None:
yield self.left(p)
if self.right(p) is not None:
yield self.right(p)
定义链式二叉树
(1) 初始化
定义非公开的_Node
类表示一个节点
在定义一个Position
类封装该节点
_validate
用来判断实例的有效性
_make_position
用来将实例进行封装
class LinkedBinaryTree(BinaryTree):
class _Node:
__slots__ = "_element","_parent","_left",'_right' # 对类的实例属性进行限制定义
def __init__(self,element,parent=None,left=None,right=None):
self._element=element
self._parent=parent
self._left=left
self._right=right
class Position(BinaryTree.Position):
def __init__(self,container,node):
self._container=container
self._node=node
def element(self):
return self._node._element
def __eq__(self, other):
return type(other) is type(self) and other._node is self._node
def _validata(self,p):
if not isinstance(p,self.Position): # 判断一个对象是否是一个已知的类型,类似 type()但是type函数不会考虑继承关系
raise TypeError('p must be a proper type')
if p._container is not self:
raise ValueError('p does not belong to this container')
return p._node
def _make_position(self,node):
return self.Position(self,node) if node is not None else None
(2)类的公开访问方法的定义:操作树现有方法的定义
def __init__(self):
self._root=None
self._size=0
def __len__(self):
return self._size
def root(self):
return self._make_position(self._root)
def parent(self,p):
node=self._validata(p)
return self._make_position(node._parent)
def left(self,p):
node=self._validata(p)
return self._make_position(node._left)
def right(self,p):
node=self._validata(p)
return self._make_position(node._right)
def num_children(self,p):
node=self._validata(p)
count=0
if node._left is not None:
count+=1
if node._right is not None:
count+=1
return count
(3)更新二叉树的操作
方法 | 功能 |
---|---|
T.add_root(e) | 为空树创建根节点,存储e |
T.add_left(p,e) | 创建新节点,存储e 位于p的左孩子 |
T.add_right(p,e) | 创新新节点 存储e 位于p的右孩子 |
T.replace(p,e) | 用e取代节点p处的元素 返回之前的元素 |
T.delete( p ) | 删除掉p节点 |
T.attach(p,T1,T2) | 将子树连接到p节点 |