当前位置: 首页 > news >正文

LeetCode 2302 统计得分小于K的子数组数目(滑动窗口)

先给出示例吧

输入:nums = [2,1,4,3,5], k = 10
输出:6
解释:
有 6 个子数组的分数小于 10 :
- [2] 分数为 2 * 1 = 2 。
- [1] 分数为 1 * 1 = 1 。
- [4] 分数为 4 * 1 = 4 。
- [3] 分数为 3 * 1 = 3 。 
- [5] 分数为 5 * 1 = 5 。
- [2,1] 分数为 (2 + 1) * 2 = 6 。
注意,子数组 [1,4] 和 [4,3,5] 不符合要求,因为它们的分数分别为 10 和 36,但我们要求子数组 的分数严格小于 10 。

这还只是我优化后的思路,本来我是借助二维数组去维护其前缀和的长度的,所以代码一开始的复杂程度可想而知

对于本题其实就是一个前缀和加滑动窗口的思想,平时按照我这个思想去写的话完全没有问题,一开始我也是分不清滑动窗口和暴力,如下面的样例所示,一开始的解决我还是按照传统意义上的双循环遍历暴力解决,所以复杂度还是o(n*n)

class Solution {public long countSubarrays(int[] nums, long k) {int n = nums.length;// int number = (n+1)*n/2;int[] s = new int[n+1];// int[][] ans = new int[n + 1][n + 1];// 计算前缀和数组for (int i = 1; i <= n; i++) {s[i] = s[i - 1] + nums[i-1];}// int key=1;long total = 0;for(int l=1;l<=n;l++){int r = l;while(r<=n){int sum = s[r]-s[l-1];// ans[r-l+1][key] = sum;if(sum*(r-l+1) < k) total++;r++;}// key++;}// for(int i=1;i<=n;i++){//     for(int j=1;j<=n;j++){//         // System.out.println("ans[i][j]:"+ans[i][j]+",i:"+i+",j:"+j);//         if(ans[i][j]!=0&&(ans[i][j]*i)<k) total++;//     }// }return total;}
}

无论怎么优化依旧还超时过不了关,这是由于在我的遍历逻辑中还是去固定了左节点,然后一一遍历,这样会导致时间复杂度过高,也就当然会超时了。而滑动窗口的根本思想是外循环右扩展,内循环左收缩,并且r和l都不需要再一一初始化,保持更新即可。
其实最难的应该就是找到最简单的对应关系能联系到题目之中。

class Solution {public long countSubarrays(int[] nums, long k) {int n = nums.length;long total = 0;long sum = 0;int r = 0;for (int l = 0; l < n; l++) {while (r < n && (sum + nums[r]) * (r - l + 1) < k) {sum += nums[r];r++;}total += r - l;sum -= nums[l];}return total;}
}

我还是解释一下题解给的答案

题解的答案很简单就是将我上述的前缀和与滑动窗口结合到了一起,说是简单,但还是很难想到的,因为大多数人的思维都是单向的解决问题的思维,如我一般就是蹦着解决目的去的,并且过程也很符合题目的描述,扯远了,对于该题解,举个例子

示例[1,2,3,4,5] k=10
第一遍遍历 1*1<10 符合
第二遍遍历(1+2)*2<10符合
第三遍遍历(1+2+3)*3>=10不符合 此时r=2并记录下total+=r-l=2 将sum的值更新为2
第四遍遍历(2+3)*2>=10不符合 此时r=2 并再次记录下total+=r-l=3 将sum的值更新为2-2=0
第五遍遍历3*1<10 符合 此时r=2,l=2
第六遍遍历(3+4)*2>=10 不符合 此时r=3,l=2 并再次记录下total+=r-l=4 将sum的值更新为3-3=0;
依次往后继续遍历

所以说这就是该代码滑动窗口设计的秒的地方,没有任何瑕疵的遍历完一个数组并得到符合条件的子数组。

http://www.xdnf.cn/news/221149.html

相关文章:

  • Mysql存储引擎、锁机制
  • (2)python之虚拟环境管理工具venv和anaconda
  • Lucene中不同搜索类型的使用方法、基本概念、应用场景、差异对比,并通过表格进行总结
  • JavaScript 作用域全面总结
  • 夜族觉醒 服务搭建 异地联机 保姆教程 流畅不卡顿
  • 【Science】强耦合手性准BIC驱动动量空间可编程高Q圆偏振激光——哈工大突破拓扑光子学新维度
  • GTC Taipei 2025 医疗域前瞻:从AI代理到医疗生态,解码医疗健康与生命科学的未来图景
  • 分享一款免费的 AI 工作流平台
  • Golang 并发编程
  • 从遍历序列构造二叉树:前序+中序与中序+后序的递归解法详解
  • USB 网卡——RNDIS 介绍
  • 数据资产:价值的源泉与释放之道
  • Langchain组件
  • 高级前端面试题:基于2025年最新技术体系
  • TS学习指南
  • 人工智能和机器学习在包装仿真中的应用与价值
  • MQTT - Android MQTT 编码实战(MQTT 客户端创建、MQTT 客户端事件、MQTT 客户端连接配置、MQTT 客户端主题)
  • Python列表全面解析:从基础到高阶操作
  • 域名转移:什么是转移码/EPP码/授权码?
  • 基于蓝耘MaaS平台进行api调用创建本地智能ai
  • 代码随想录第39天|leetcode198.打家劫舍、leetcode213.打家劫舍II 、leetcode337.打家劫舍III
  • 4月29日日记
  • 【浙江大学DeepSeek公开课】DeepSeek的本地化部署与AI通识教育之未来
  • 高等数学-第七版-下册 选做记录 习题9-5
  • 【记】Laya2.x数字末尾导致换行异常问题
  • Promtail+Loki+Grafana监控日志
  • AD系列:Windows Server 2025 搭建AD域控和初始化
  • 一文读懂 JavaScript 中的深浅拷贝
  • IEC61499编程方式与传统PLC编程方式比较
  • 生态修复项目管理软件