刷算法题,从来不是为了记题,而是练习把实际的问题抽象成具体的数据结构或算法模型,然后利用对应的数据结构或算法模型来进行解题。个人觉得,带着这种思维刷题,不仅能解决面试问题,也能更多的学会在日常工作中思考,如何将实际的场景抽象成相应的算法模型,从而提高代码的质量和性能
二叉树的层序遍历 II
题目来源:LeetCode-107. 二叉树的层序遍历 II
题目描述
给定一个二叉树,返回其节点值自底向上的层序遍历。 (即按从叶子节点所在层到根节点所在的层,逐层从左向右遍历)
示例
示例 1
给定二叉树 [3,9,20,null,null,15,7]
3
/ \
9 20
/ \
15 7
复制代码
返回其自底向上的层序遍历为:
[
[15,7],
[9,20],
[3]
]
复制代码
解题
解法一:广度优先搜索(BFS)
思路
从根节点开始的层序遍历很简单,就是常规的广度优先搜索思想,借助队列来记录每一层的节点,然后进行遍历输出。本题是希望从根节点开始,逐层的遍历树的节点
核心思想其实是一样的,同样是广度优先搜索的思想。对于用Go语言实现,这种方式最好
- 从根节点开始,常规的进行层序遍历(注意:每次遍历会获取该层所有的数据)
- 将每层获取的结果放入结果集当中
- 将结果集的首尾进行置换(因为Go语言的特性,这一点很容易做到)
代码
//二叉树的层序遍历II(从叶子结点开始,往上进行层序遍历)
func levelOrderBottom(root *TreeNode) [][]int {
if root == nil {
return [][]int{}
}
res := [][]int{}
nodeQueue := []*TreeNode{root}
for len(nodeQueue) != 0 {
levelVals := []int{}
size := len(nodeQueue)
for i := 0; i< size; i++ {
node := nodeQueue[0]
nodeQueue = nodeQueue[1:]
levelVals = append(levelVals, node.Val)
if node.Left != nil {
nodeQueue = append(nodeQueue, node.Left)
}
if node.Right != nil {
nodeQueue = append(nodeQueue, node.Right)
}
}
res = append(res, levelVals)
}
//置换
for j:=0; j < len(res)/2; j++ {
res[j], res[len(res)-j-1] = res[len(res)-j-1], res[j]
}
return res
}
复制代码