技术经验解读:【LeetCode】560.SubarraySumEqualsK子数组和为K

简介: 技术经验解读:【LeetCode】560.SubarraySumEqualsK子数组和为K

Given an array of integers and an integer k, you need to find the total number of continuous subarrays whose sum equals to k.


Example 1:


Input:nums = 【1,1,1】, k = 2


Output: 2


Note:


The length of the array is in range 【1, 20,000】.


The range of numbers in the array is 【-1000, 1000】 and the range of the integer k is 【-1e7, 1e7】.


这道题给了我们一个数组,让求和为k的连续子数组的个数,博主最开始看到这道题想着肯定要建立累加和数组啊,然后遍历累加和数组的每个数字,首先看其是否为k,是的话结果 res 自增1,然后再加个往前的循环,这样可以快速求出所有的子数组之和,看是否为k,参见代码如下:


解法一:


class Solution {


public:


int subarraySum(vector[span style="color: rgba(0, 0, 255, 1)">int

int res = 0, n = nums.size();


vector[span style="color: rgba(0, 0, 255, 1)">int

for (int i = 1; i < n; ++i) {


sums【i】 = sums【i - 1】 + nums【i】;


}


for (int i = 0; i < n; ++i) {


if (sums【i】 == k) ++res;


for (int j = i - 1; j >= 0; --j) {


if (sums【i】 - sums【j】 == k) ++res;


}


}


return res;


}


};


上面的求累加和的方法其实并没有提高程序的执行效率,跟下面这种暴力搜索的解法并没有什么不同,博主很惊奇 OJ 居然这么大度,让这种解法也能通过,参见代码如下:


解法二:


class Solution {


public:


int //代码效果参考:http://www.lyjsj.net.cn/wx/art_22916.html

subarraySum(vector[span style="color: rgba(0, 0, 255, 1)">int

int res = 0, n = nums.size();


for (int i = 0; i < n; ++i) {


int sum = nums【i】;


if (sum == k) ++res;


for (int j = i + 1; j < n; ++j) {


sum += nums【j】;


if (sum == k) ++res;


}


}


return res;


}


};


论坛上大家比较推崇的其实是这种解法,用一个 HashMap 来建立连续子数组之和跟其出现次数之间的映射,初始化要加入 {0,1} 这对映射,这是为啥呢,因为解题思路是遍历数组中的数字,用 sum 来记录到当前位置的累加和,建立 HashMap 的目的是为了可以快速的查找 sum-k 是否存在,即是否有连续子数组的和为 sum-k,如果存在的话,那么和为k的子数组一定也存在,这样当 sum 刚好为k的时候,那么数组从起始到当前位置的这段子数组//代码效果参考:http://www.lyjsj.net.cn/wx/art_22914.html

的和就是k,满足题意,如果 HashMap 中事先没有 m【0】 项的话,这个符合题意的结果就无法累加到结果 res 中,这就是初始化的用途。上面讲解的内容顺带着也把 for 循环中的内容解释了,这里就不多阐述了,有疑问的童鞋请在评论区留言哈,参见代码如下:

解法三:


class Solution {


public:


int subarraySum(vector[span style="color: rgba(0, 0, 255, 1)">int

int res = 0, sum = 0, n = nums.size();


unordered_map[span style="color: rgba(0, 0, 255, 1)">int, int

for (int i = 0; i < n; ++i) {


sum += nums【i】;


res += m【sum - k】;


++m【sum】;


}


return res;


}


};


Github 同步地址:


类似题目:


Two Sum


Continuous Subarray Sum


Subarray Product Less Than K


Find Pivot Index


参考资料:


LeetCode All in One 题目讲解汇总(持续更新中...)


(欢迎加入博主的知识星球,博主将及时答疑解惑,并分享刷题经验与总结,快快加入吧~)


喜欢请点赞,疼爱请打赏~.~


Venmo 打赏

相关文章
|
7月前
|
存储 算法
LeetCode刷题---209. 长度最小的子数组(双指针-滑动窗口)
LeetCode刷题---209. 长度最小的子数组(双指针-滑动窗口)
|
4月前
|
算法 Python
【Leetcode刷题Python】子数组查找
一个用于寻找给定字符串中最长重复子串的Python函数实现,采用了滑动窗口的方法来检测重复的子串。
21 1
|
4月前
|
算法 Java
LeetCode初级算法题:子数组最大平均数+二叉树的最小深度+最长连续递增序列+柠檬水找零
LeetCode初级算法题:子数组最大平均数+二叉树的最小深度+最长连续递增序列+柠檬水找零
44 0
|
6月前
|
算法 测试技术 程序员
力扣经典150题第三十题:长度最小的子数组
力扣经典150题第三十题:长度最小的子数组
32 1
|
5月前
|
存储 算法
经典的滑动窗口的题目 力扣 2799. 统计完全子数组的数目(面试题)
经典的滑动窗口的题目 力扣 2799. 统计完全子数组的数目(面试题)
|
6月前
【LeetCode刷题】滑动窗口思想解决问题:长度最小的子数组、无重复字符的最长子串
【LeetCode刷题】滑动窗口思想解决问题:长度最小的子数组、无重复字符的最长子串
|
7月前
【力扣】209. 长度最小的子数组
【力扣】209. 长度最小的子数组
|
7月前
|
算法 测试技术
每日一题:LeetCode-209. 长度最小的子数组(滑动窗口)
每日一题:LeetCode-209. 长度最小的子数组(滑动窗口)
|
7月前
|
索引
leetcode代码记录(最长重复子数组
leetcode代码记录(最长重复子数组
45 0
|
7月前
leetcode代码记录(长度最小的子数组
leetcode代码记录(长度最小的子数组
36 0