leetcode199.题目描述
给定一棵二叉树,想象自己站在它的右侧,按照从顶部到底部的顺序,返回从右侧所能看到的节点值。
解决思路: 1.错误思路,用递归来循环保存右边节点,如果右边节点为None,则跳到保存左边节点,不能解决以下图片情况:
2.正确思路,采用广度优先搜索算法来遍历整个二叉树,但是需要一个标记来记忆每个node的深度,最后将每一层最后的node节点的value保存下来即可。
广度优先遍历通俗讲解:从二叉树第一层到最底层,每一层从左到右的访问每个节点的value。通常我们采用队列先进先出的数据结构,访问每个node时,将改节点的左右节点按顺序加入到队列中。以上图作为例子:
node1先入队列,队列此时为[node1],将node1出队,分别将node1的左右节点node2和node3入队,此时队列情况为[node2,node3];然后node2出队,并将node2的左右节点node4和node5加入到队列中来,此时队列的情况为[node3,node4,node5]; 然后我们将node3出队,加入node3的左右节点,此时队列情况为[node4,node5,node6],因为node3的左节点为空,没有加入到队列中来… 经过不断循环后,直到队列为空,即访问了二叉树的所有节点。
python代码如下:
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, x):
# self.val = x
# self.left = None
# self.right = None
#上面为二叉树的每个节点的类定义说明
class Solution:
def __init__(self):
self.res = dict() #定义字典来保存节点
def rightSideView(self, root: TreeNode) -> List[int]:
if not root: #边界值判断:如果root为空直接返回空列表即可
return []
deque = [] #定义列表,可以作为队列来使用
depth = 0 #depth表示深度,为每个node添加一个标记,即深度信息
deque.append((root,depth)) #树的加入头结点,同时加入标记信息
#二叉树的广度遍历
while(deque):
current,depth = deque.pop(0) #用列表模拟出队
self.res[depth] = current.val
if current.left: #判断其左节点是否为空
deque.append((current.left,depth+1)) #列表模拟入队,加入左节点,和标记深度信息
if current.right:#判断其右节点是否为空
deque.append((current.right,depth+1))#列表模拟入队,加入右节点,和深度信息
return [self.res[i] for i in range(depth+1)] #返回列表生成式,最后得到的列表,通过列表生成式将字典转为列表
代码讲解: 看代码中的注释,注释非常详细