子串—和为K的子数组统计

核心逻辑:

  1. 前缀和:preSum表示从数组开头到当前元素的总和
  2. 公式:preSum[j] - pre[i] =k ——> 子数组i+1~j的和 =k
  3. 转化成: 找preSum[i] = pre[j] - k
  4. 用哈希表记录每个前缀和出现的次数,实现O(1)查询

关键细节

  • predixMap[0] = 1必须写
  • 作用:处理从数组第一个元素开始的子数组
  • 每次先查preSum - k是否存在,再把当前前缀和存入map
  • 不能先存再查,否则会重复统计当前位置

复杂度:

  • 时间:O(n)
  • 空间:O(n)

总结

  1. 这是最优解法,暴力会超时
  2. 核心:前缀和 + 哈希表
  3. 记住初始状态
  4. C++ 用 unordered_map 实现

完整代码实现如下:

#include
#include
#include <unordered_map>
using namespace std;

int subarraySum(vector& nums, int k) {

unordered_map<int, int> prefixMap;
prefixMap[0] = 1; // 关键:前缀和 0 出现 1 次
int preSum = 0;
int count = 0;

for (int num : nums) {
preSum += num; // 计算当前前缀和

// 如果 preSum - k 存在,就累加次数
if (prefixMap.find(preSum - k) != prefixMap.end()) {
count += prefixMap[preSum - k];
}

// 把当前前缀和加入哈希表
prefixMap[preSum]++;
}
return count;
}

// 测试
int main() {
vector nums1 = {1,1,1};
int k1 = 2;
cout << subarraySum(nums1, k1) << endl; // 输出 2

vector nums2 = {1,2,3};
int k2 = 3;
cout << subarraySum(nums2, k2) << endl; // 输出 2

return 0;
}

posted @ 2026-03-26 13:20  ZealousMclaren  阅读(20)  评论(0)    收藏  举报