【java】剑指offer34_二叉树中和为某一值的路径

122 篇文章 0 订阅

题目描述

输入一棵二叉树和一个整数,打印出二叉树中节点值的和为输入整数的所有路径。从树的根节点开始往下一直到叶节点所经过的节点形成一条路径。

示例:
给定如下二叉树,以及目标和 sum = 22,

              5
             / \
            4   8
           /   / \
          11  13  4
         /  \    / \
        7    2  5   1
返回:

[
   [5,4,11,2],
   [5,8,4,5]
]
提示:节点总数 <= 10000

参考思路:回溯

  • 先序遍历: 按照 “根、左、右” 的顺序,遍历树的所有节点。
  • 路径记录: 在先序遍历中,记录从根节点到当前节点的路径。当路径为 ① 根节点到叶节点形成的路径 且 ② 各节点值的和等于目标值 sum 时,将此路径加入结果列表。

pathSum(root, sum) 函数:

  • 初始化: 结果列表 array ,路径列表 list 。
  • 返回值: 返回 array 即可。

sumDFS(root, sum, temp,list) 函数:

  • 递推参数: 当前节点 root ,目标值sum ,当前节点值的和 temp,节点路径集合列表list 。
  • 终止条件: 若节点 root 为空,则直接返回。
  • 递推工作:
  1. 路径更新: 将当前节点值 root.val 加入路径 list ;
  2. 目标值更新: temp += root.val(即目标值 temp 从 0增加至sum  );
  3. 路径记录: 当 ① root 为叶节点 且 ② 路径和等于目标值 ,则将此路径 list 加入array 。
  4. 先序遍历: 递归左 / 右子节点。
  5. 路径恢复: 向上回溯前,需要将当前节点从路径 list 中删除,即执行 list.remove() 。

小tips:

  1. 记录路径时若直接执行 array.add(list) ,则是将 list 对象加入了 array ;后续 list 改变时, array 中的 list 对象也会随之改变,正确做法:array.add(new ArrayList<>(list)) ,相当于复制了一个 list 并加入到 array 。
  2. 路径子节点集合值在向上回溯时不需要减掉之前路径节点相应的值,因为这里int值是深拷贝,基本数据类型传递给方法的是变量的值(深拷贝)而不是实际的存储值变量的地址(浅拷贝)
// 定义全局List存储二维数组
    private List<List<Integer>> array = new ArrayList<>();

    public List<List<Integer>> pathSum(TreeNode root, int sum) {
        List<Integer> list = new ArrayList<>(); // 定义合理路径集合
        sumDFS(root,sum,0,list); // dfs
        return array;
    }

    public void sumDFS(TreeNode root, int sum, int temp, List<Integer> list) {
        // 节点为空边界限制
        if (root == null) {
            return ;
        }
        temp += root.val; // 目前所以子节点的和
        list.add(root.val); // 追加进节点路径集合
        // 子节点路径和与目标值相等且左右子节点为空--避免负数节点情况
        if (temp == sum && root.left == null && root.right == null) {
            array.add(list);
        }
        // 递归左右子节点
        if (root.left != null) {
            sumDFS(root.left, sum, temp, list);
        }
        if (root.right != null) {
            sumDFS(root.right, sum, temp, list);
        }
        // 回溯退回节点值
        list.remove(list.size()-1);
    }

复杂度分析:
时间复杂度 O(N) : N为二叉树的节点数,先序遍历需要遍历所有节点。
空间复杂度 O(N): 最差情况下,即树退化为链表时,list 存储所有树节点,使用 O(N) 额外空间。

作者:jyd
链接:https://leetcode-cn.com/problems/er-cha-shu-zhong-he-wei-mou-yi-zhi-de-lu-jing-lcof/solution/mian-shi-ti-34-er-cha-shu-zhong-he-wei-mou-yi-zh-5/

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值