Java描述 LeetCode,437. 路径总和 III

𝑰’𝒎 𝒉𝒉𝒈, 𝑰 𝒂𝒎 𝒂 𝒈𝒓𝒂𝒅𝒖𝒂𝒕𝒆 𝒔𝒕𝒖𝒅𝒆𝒏𝒕 𝒇𝒓𝒐𝒎 𝑵𝒂𝒏𝒋𝒊𝒏𝒈, 𝑪𝒉𝒊𝒏𝒂.

  • 🏫 𝑺𝒉𝒄𝒐𝒐𝒍: 𝑯𝒐𝒉𝒂𝒊 𝑼𝒏𝒊𝒗𝒆𝒓𝒔𝒊𝒕𝒚
  • 🌱 𝑳𝒆𝒂𝒓𝒏𝒊𝒏𝒈: 𝑰’𝒎 𝒄𝒖𝒓𝒓𝒆𝒏𝒕𝒍𝒚 𝒍𝒆𝒂𝒓𝒏𝒊𝒏𝒈 𝒅𝒆𝒔𝒊𝒈𝒏 𝒑𝒂𝒕𝒕𝒆𝒓𝒏, 𝑳𝒆𝒆𝒕𝒄𝒐𝒅𝒆, 𝒅𝒊𝒔𝒕𝒓𝒊𝒃𝒖𝒕𝒆𝒅 𝒔𝒚𝒔𝒕𝒆𝒎, 𝒎𝒊𝒅𝒅𝒍𝒆𝒘𝒂𝒓𝒆 𝒂𝒏𝒅 𝒔𝒐 𝒐𝒏.
  • 💓 𝑯𝒐𝒘 𝒕𝒐 𝒓𝒆𝒂𝒄𝒉 𝒎𝒆:𝑽𝑿
  • 📚 𝑴𝒚 𝒃𝒍𝒐𝒈: 𝒉𝒕𝒕𝒑𝒔://𝒉𝒉𝒈𝒚𝒚𝒅𝒔.𝒃𝒍𝒐𝒈.𝒄𝒔𝒅𝒏.𝒏𝒆𝒕/
  • 💼 𝑷𝒓𝒐𝒇𝒆𝒔𝒔𝒊𝒐𝒏𝒂𝒍 𝒔𝒌𝒊𝒍𝒍𝒔:𝒎𝒚 𝒅𝒓𝒆𝒂𝒎

1-1: Overview

给定一个二叉树的根节点 root ,和一个整数 targetSum ,求该二叉树里节点值之和等于 targetSum 的 路径 的数目。

路径 不需要从根节点开始,也不需要在叶子节点结束,但是路径方向必须是向下的(只能从父节点到子节点)。

示例 1:

输入:root = [10,5,-3,3,2,null,11,3,-2,null,1], targetSum = 8
输出:3
解释:和等于 8 的路径有 3 条,如图所示。

示例 2:

输入:root = [5,4,8,11,null,13,4,7,2,null,null,5,1], targetSum = 22
输出:3

提示:

二叉树的节点个数的范围是 [0,1000]
-109 <= Node.val <= 109 
-1000 <= targetSum <= 1000 

通过次数159,510提交次数279,189

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/path-sum-iii
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

1-2: Solution

你看的懂官网或者那个精选的代码吗?我是看不懂的。。或者说有些地方,他们觉得简单没写吧。所以,我再自己写一个,只为了之后多刷打基础。

variables:,少就少在没有给一些变量作解释。对新手不友好啊

  • prefix sum: the sum of nodes from the root to the current.
  • map: key: the current prefix sum of the path; value: the number of the nodes whoes prefix sum equal to the key.
  • cur: the prefix sum of the current node (including the current node)
  • res: count the result which meets the requirements of the question.

  • prefix sum: 前缀和,总根节点到当前节点的值的和
  • map: key: 某个节点的前缀和; value: 前缀和=key的一共有多少个.
  • cur: 当前节点的前缀和
  • res: 计数符合要求的答案(个数)

正常来说,判断是否有前缀和等于某一条路径的时候应该用true和false啊,那这里map的value为什么不是Boolean呢?你看,这里节点的值有正有负,所以和等于某一条路径的,可能不止一条。

Example:
count the targetSum == 5 找到路径等于5的例子
![在这里插入图片描述](https://img-blog.csdnimg.cn/0c339b43713a436d9fd3afec8aef1c97.png?x-oss-process=image/watermark,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBA5rKz5rW35ZOleXlkcw==,size_11,color_FFFFFF,t_70,g_se,x_16
Why use a vitrtual node? Think the linked list which has one external head. In this situation, the function is the same. At the same time, I recall that dp use external space to simplify the initail process.
为什么用虚拟节点?就像是单链表中额外的头结点,同时我又想到了dp中,通过那额外的一行一列,使得初始化过程简单,甚至避免了初始化。这里仅仅是为了,大家都有一个标杆,root节点也有了依靠。

public class Solution {
    Map<Long, Integer> map = new HashMap<>();
    int res = 0;

    public int pathSum(TreeNode root, int targetSum) {
        // 这里就是那个虚拟节点
        map.put(0L, 1);
        dfs(root, 0, targetSum);
        return res;
    }

    public void dfs(TreeNode root, long cur, int targetSum) {
        if (root == null) {
            return;
        }
        cur += root.val;
        res += map.getOrDefault(cur - targetSum, 0);
        map.put(cur, map.getOrDefault(cur, 0) + 1);
        dfs(root.left, cur, targetSum);
        dfs(root.right, cur, targetSum);
        // 回溯,至于为什么这么写,你需要基本的回溯常识,这里因为我很明白,所以就不写了,
        // 注意cur为什么不用回溯?因为cur是局部变量,而map是递归过程中公用的
        map.put(cur, map.getOrDefault(cur, 0) - 1);
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

河海哥yyds

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值