题目描述
输入一颗二叉树的根节点root和一个整数expectNumber,找出二叉树中结点值的和为expectNumber的所有路径。
1.该题路径定义为从树的根结点开始往下一直到叶子结点所经过的结点
2.叶子节点是指没有子节点的节点
3.路径只能从父节点到子节点,不能从子节点到父节点
4.总节点数目为n
如二叉树root为{10,5,12,4,7},expectNumber为22
则合法路径有[[10,5,7],[10,12]]
原题链接:NC8 二叉树中和为某一值的路径(二)
思路
题目思路比较简单,是典型的二叉树的递归问题,题目描述中最值得注意的事情是路径指的是根结点到叶结点的完整路径。
- 深度遍历搜索路径
- 递归每一步:搜索左子树和右子树并回溯
- 出口:当前路径和等于期待数并且走到了叶节点
- 使用两个list存储输出的结果和当前搜索路径
递归
简单的递归+回溯没什么好说的,最重要的处理是对当前路径的处理,也就是理解什么时候加入到list里什么时候把它拿走,也就是理解回溯的过程。
public void dfs(TreeNode node,int expectNumber,int sum){
sum+=node.val;
list.add(node.val);
if(sum==expectNumber && node.left==null && node.right==null){
res.add(new ArrayList<>(list));
return;
}
if(node.left!=null){
dfs(node.left,expectNumber,sum);
list.remove(list.size()-1);
}
if(node.right!=null){
dfs(node.right,expectNumber,sum);
list.remove(list.size()-1);
}
}
总结
- 其实就是个前序遍历,不知道为什么题目难度的定位是中等,甚至上一道题是较难,说一下我对回溯的理解吧。你走到一个节点,一定要考虑是走左孩子还是右孩子,比如先走左,走的过程一定把这个节点添加到了list里边,那走完左孩子下边的左子树,然后要走右边,那么这个时候就一定要把走完的左孩子从list里拿走,这样回溯也就很顺理成章了。
- 解决了每一步要做什么,考虑好出口题目也就做完了。当然这个出口还是比较重要的,最开始我就是没有考虑要走到叶节点后面的用例就报错了,这样的路径和问题总体比较简单,大致要考虑的也就是节点是不是可以重复走以及起点和终点的限制了。