一、构建与遍历二叉树

基本性质
1)在二叉树的第i层上最多有2i-1 个节点 。(i>=1)
2)二叉树中如果深度为k,那么最多有2k-1个节点。(k>=1)
3)在完全二叉树中,具有n个节点的完全二叉树的深度为[log2n]+1,其中[log2n]是向下取整。向下取整就是小数点后面的数字无论多少,都只取前面的整数。

4)二叉树的存储可以顺序存储即数组形式,也可以链式存储。

class Node(object):
def __init__(self,item):
self.key=item
self.left=None
self.right=None
class BinaryTree(object):
def __init__(self):
self.root=None def addNode(self,item):
new_node = Node(item)
if self.root is None:
self.root=new_node
else:
stack=[]
stack.append(self.root)
while True:
node=stack.pop(0)
if node.left is None:
node.left=new_node
return
elif node.right is None:
node.right=new_node
return
else:
stack.append(node.left)
stack.append(node.right) def traverse(self): #层次遍历
if self.root is None:
return None
else:
s=[]
s.append(self.root)
while len(s) > 0:
node = s.pop(0)
print(node.key)
if node.left is not None:
s.append(node.left)
if node.right is not None:
s.append(node.right)
#一层层打印
def Print(self, pRoot):
if pRoot is None:
return []
l=[]
s=[]
s.append(pRoot)
while len(s)>0:
length=len(s)
v=[]
for i in range(length):
tmp=s.pop(0)
v.append(tmp.val) if tmp.left:
s.append(tmp.left)
if tmp.right:
s.append(tmp.right)
l.append(v)
return l

def preOrder(self,root):
if root is None:
return None
print(root.key)
self.preOrder(root.left)
self.preOrder(root.right) def inOrder(self,root):
if root is None:
return None self.inOrder(root.left)
print(root.key)
self.inOrder(root.right) def postOrder(self,root):
if root is None:
return None self.postOrder(root.left)
self.postOrder(root.right)
print(root.key)

 之字形打印二叉树

def print(root):
if root is None:
return None
s1=[]
s2=[]
s1.append(root)#靠两个栈交替左右压入栈,实现左右交替输出,形成之字形打印
while len(s1)>0 or len(s2)>0:
while len(s1)>0:
tmp=s1.pop()
print(tmp.value)
if tmp.left is not None:
s2.append(tmp.left)
if tmp.right is not None:
s2.append(tmp.right)
while len(s2)>0:
tmp=s2.pop()
print(tmp.value)
if tmp.right is not None:
s1.append(tmp.right)
if tmp.left is not None:
s1.append(tmp.left)

非递归前序遍历:

def PreOrderWithoutRecursion(root):
if root is None:
return
s=[]
p=root
while len(s)>0 or p is not None:
if p is not None:
print(p.key)
s.append(p)
p=p.left
else:
p=s.pop()
p=p.right

非递归中序遍历:

def InOrderWithoutRecursion(root):
if root is None:
return
s=[]
p=root
while len(s)>0 or p is not None:
if p is not None:
s.append(p)
p=p.left
else:
p=s.pop()
print(p.key)
p=p.right

非递归后序遍历:

def PostOrderWithoutRecursion(root):
if root is None:
return
s=[]
p=root
lastVisit=None
while p is not None:
s.append(p)
p=p.left
while len(s)>0:
p=s.pop()
if p.right==None or lastVisit==p.right:
print(p.key)
lastVisit=p
else:
s.append(p)
p=p.right
while p is not None:
s.append(p)
p=p.left

二、二叉树的宽度与深度

def treeDepth(root):
if root is None:
return 0
nleft=treeDepth(root.left)+1
nright=treeDepth(root.right)+1
return nleft if nleft > nright else nright #求解二叉树的宽度,节点数最多的一层的节点数即为二叉树的宽度
def treeWidth(root):
if root is None:
return 0
max_width=0
s=[]
s.append(root)
while len(s)>0:
width=len(s)
if width>max_width:
max_width=width
for i in range(width):
node=s.pop(0)
if node.left is not None:
s.append(node.left)
if node.right is not None:
s.append(node.right) return max_width

 三、判断是否为子树

#如果两个节点值相同,则继续判断下面节点值是否也相等
def isPart(pRoot1,pRoot2):
if pRoot2 is None:
return True
if pRoot1 is None:
return False
if pRoot1.val!=pRoot2.val:
return False
return isPart(pRoot1.left,pRoot2.left) and isPart(pRoot1.right,pRoot2.right) def HasSubtree(pRoot1, pRoot2):
res=False
if pRoot1 is not None and pRoot2 is not None:
if pRoot1.val==pRoot2.val:
res=isPart(pRoot1,pRoot2)
if not res:
res=HasSubtree(pRoot1.left,pRoot2)
if not res:
res=HasSubtree(pRoot1.right,pRoot2)
return res

 四、判断是否为平衡二叉树

def TreeDepth(self,root):
if root is None:
return 0
nleft=self.TreeDepth(root.left)
nright=self.TreeDepth(root.right)
return nleft+1 if nleft>nright else nright+1 def IsBalanced_Solution(self, pRoot):
isBalance=True
if pRoot is None:
return isBalance
leftDepth=self.TreeDepth(pRoot.left)
rightDepth=self.TreeDepth(pRoot.right)
if abs(leftDepth-rightDepth)>1:
isBalance=False
return isBalance and self.IsBalanced_Solution(pRoot.left) and self.IsBalanced_Solution(pRoot.right)

五、判断是否为对称二叉树

def isSame(self,left,right):
if left and right :
if left.val==right.val:
return self.isSame(left.left,right.right) and self.isSame(left.right,right.left)
else:
return False
elif not left and not right:
return True
else:
return False
def isSymmetrical(self, pRoot):
if pRoot is None:
return True
return self.isSame(pRoot.left,pRoot.right)

 六、序列化与反序列化

def Serialize(self, root):
if root is None:
return '#'
return str(root.val)+self.Serialize(root.left)+self.Serialize(root.right)
def Deserialize(self, s):
if len(s)<=0:
return None
root=None
val=s.pop(0)
if val!='#':
root=TreeNode(int(val))
root.left=self.Deserialize(s)
root.right=self.Deserialize(s)
return root

七、查找二叉树某个值的路径(先根方式)

def findval(root,val):
if root is None:
return None
s=[]
p=root
path=[] #利用先根遍历的方式进行查找,path保存那些右子树不为空的根节点,进入path说明遍历过了,以便后续判断何时出栈。
while len(s)>0 or p is not None:
if p is not None:
if p in path:
s.pop()#如果在path中了,说明之前遍历过来,就直接出栈吧,不用再向下子树遍历了
else:
s.append(p)
if p.key==val:
return s
p=p.left
else:
p=s[len(s)-1]#暂时先不出栈,看看右子树是否为空,右子树不为空,就暂时不出栈
if p.right is None or p in path:#右子树为空的,或者之前遍历过的就直接出栈吧
s.pop()
p=None
else:
path.append(p) #之前没遍历过的且其右子树不为空,那就先不出栈了,放入path中,表示遍历过了。
p=p.right

例如上图中:E的路径就是A,C ,E。  F的路径就是A,C,F.

 

参考来源:https://www.jianshu.com/p/bf73c8d50dc2

 

python 实现二叉树相关算法的更多相关文章

  1. 二叉树-你必须要懂!(二叉树相关算法实现-iOS)

    这几天详细了解了下二叉树的相关算法,原因是看了唐boy的一篇博客(你会翻转二叉树吗?),还有一篇关于百度的校园招聘面试经历,深刻体会到二叉树的重要性.于是乎,从网上收集并整理了一些关于二叉树的资料,及 ...

  2. python实现二叉树遍历算法

    说起二叉树的遍历,大学里讲的是递归算法,大多数人首先想到也是递归算法.但作为一个有理想有追求的程序员.也应该学学非递归算法实现二叉树遍历.二叉树的非递归算法需要用到辅助栈,算法着实巧妙,令人脑洞大开. ...

  3. 数据结构-二叉搜索树和二叉树排序算法(python实现)

    今天我们要介绍的是一种特殊的二叉树--二叉搜索树,同时我们也会讲到一种排序算法--二叉树排序算法.这两者之间有什么联系呢,我们一起来看一下吧. 开始之前呢,我们先来介绍一下如何创建一颗二叉搜索树. 假 ...

  4. [0x00 用Python讲解数据结构与算法] 概览

    自从工作后就没什么时间更新博客了,最近抽空学了点Python,觉得Python真的是很强大呀.想来在大学中没有学好数据结构和算法,自己的意志力一直不够坚定,这次想好好看一本书,认真把基本的数据结构和算 ...

  5. Python实现各种排序算法的代码示例总结

    Python实现各种排序算法的代码示例总结 作者:Donald Knuth 字体:[增加 减小] 类型:转载 时间:2015-12-11我要评论 这篇文章主要介绍了Python实现各种排序算法的代码示 ...

  6. NLP︱高级词向量表达(一)——GloVe(理论、相关测评结果、R&python实现、相关应用)

    有很多改进版的word2vec,但是目前还是word2vec最流行,但是Glove也有很多在提及,笔者在自己实验的时候,发现Glove也还是有很多优点以及可以深入研究对比的地方的,所以对其进行了一定的 ...

  7. 用Python实现随机森林算法,深度学习

    用Python实现随机森林算法,深度学习 拥有高方差使得决策树(secision tress)在处理特定训练数据集时其结果显得相对脆弱.bagging(bootstrap aggregating 的缩 ...

  8. Python面对对象相关知识总结

    很有一段时间没使用python了,前两天研究微信公众号使用了下python的django服务,感觉好多知识都遗忘了,毕竟之前没有深入的实践,长期不使用就忘得快.本博的主要目的就是对Python中我认为 ...

  9. PAT甲级 二叉树 相关题_C++题解

    二叉树 PAT (Advanced Level) Practice 二叉树 相关题 目录 <算法笔记> 重点摘要 1020 Tree Traversals (25) 1086 Tree T ...

随机推荐

  1. 【APS.NET Core】- 应用程序Startup类介绍

    转自:https://www.cnblogs.com/stulzq/p/7845026.html Startup类配置服务和应用程序的请求管道. Startup 类 ASP.NET Core应用程序需 ...

  2. tcp传送报文

    707 void tcp_init_xmit_timers(struct sock *sk)708 {709     inet_csk_init_xmit_timers(sk, &tcp_wr ...

  3. delphi怎样单步调试

    在delphi的IDE编辑窗口里,主菜单->Run->Step Over或者主菜单->Run->Trace Into单步调试有两种方式:一种是Step Over,快捷键是F8, ...

  4. ismember matlab

    ismember 判断A中的元素在B中有没有出现 LIA = ismember(A,B) for arrays A and B returns an array of the same size as ...

  5. 9.1、AutoEncoder自动编码器[转]

    如果给定一个神经网络,我们假设其输出与输入是相同的,然后训练调整其参数,得到每一层中的权重.自然地,我们就得到了输入I的几种不同表示(每一层代表一种表示),这些表示就是特征.自动编码器就是一种尽可能复 ...

  6. bzoj3782上学路线

    题意:从n*m网格图的左下角走到右上角(n,m<=10^10),有t个坐标不能经过(t<=200),只能向上向右走,问有多少种不同的走法,对p取模, p只有两种取值,1000003(质数) ...

  7. 【bzoj4300】绝世好题 dp

    题目描述 给定一个长度为n的数列ai,求ai的子序列bi的最长长度,满足bi&bi-1!=0(2<=i<=len). 输入 输入文件共2行. 第一行包括一个整数n. 第二行包括n个 ...

  8. Socket_SSH-3(粘包)

    粘包:两次数据粘到一起了.在Windows中基本看不出来效果. 服务器端的配置: import socket,os,time server=socket.socket() server.bind((' ...

  9. 转:浅谈Spectral Clustering 谱聚类

    浅谈Spectral Clustering Spectral Clustering,中文通常称为“谱聚类”.由于使用的矩阵的细微差别,谱聚类实际上可以说是一“类”算法. Spectral Cluste ...

  10. [洛谷P4092][HEOI2016/TJOI2016]树

    题目大意:给你一棵树,有两个操作: $C\;x:$给第$x$个节点打上标记 $Q\;x:$询问第$x$个节点的祖先中最近的打过标记的点(自己也是自己的祖先) 题解:树剖,可以维护区间或,然后若一段区间 ...