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

​LeetCode解法汇总307. 区域和检索 - 数组可修改

 目录链接:

力扣编程题-解法汇总_分享+记录-CSDN博客

GitHub同步刷题项目:

https://github.com/September26/java-algorithms

原题链接:力扣(LeetCode)官网 - 全球极客挚爱的技术成长平台


描述:

给你一个数组 nums ,请你完成两类查询。

  1. 其中一类查询要求 更新 数组 nums 下标对应的值
  2. 另一类查询要求返回数组 nums 中索引 left 和索引 right 之间( 包含 )的nums元素的  ,其中 left <= right

实现 NumArray 类:

  • NumArray(int[] nums) 用整数数组 nums 初始化对象
  • void update(int index, int val) 将 nums[index] 的值 更新 为 val
  • int sumRange(int left, int right) 返回数组 nums 中索引 left 和索引 right 之间( 包含 )的nums元素的  (即,nums[left] + nums[left + 1], ..., nums[right]

示例 1:

输入:
["NumArray", "sumRange", "update", "sumRange"]
[[[1, 3, 5]], [0, 2], [1, 2], [0, 2]]
输出:
[null, 9, null, 8]解释:
NumArray numArray = new NumArray([1, 3, 5]);
numArray.sumRange(0, 2); // 返回 1 + 3 + 5 = 9
numArray.update(1, 2);   // nums = [1,2,5]
numArray.sumRange(0, 2); // 返回 1 + 2 + 5 = 8

提示:

  • 1 <= nums.length <= 3 * 104
  • -100 <= nums[i] <= 100
  • 0 <= index < nums.length
  • -100 <= val <= 100
  • 0 <= left <= right < nums.length
  • 调用 update 和 sumRange 方法次数不大于 3 * 104 

解题思路:

这题数组的长度为310^4,如果时间复杂度是O(n2),则会超时。所以这题一定不能每次都遍历。 
但是我们可以发现一个规律,就是update的时候,影响的范围很小,甚至有可能都对sumRange不产生影响,所以,我们可以把影响范围缩减到最小。
我们可以把nums数组划分为k块,暂且用N1,N2,Nk表示,则left和right会出现2种情况。 
left和right属于同一块:这种情况,直接求left和right的累加值即可。 
left和right不属于同一块:这种情况,求left到其所属块的尾之间的和,right所属的块的头到right之间的和,以及left和right之间的块的和。三者相加,就是最终值。

代码:

class NumArray {private int[] nums;private int[] pieces;private int pieceLength;public NumArray(int[] nums) {this.nums = nums;pieceLength = (int) Math.ceil(Math.sqrt(nums.length));pieces = new int[nums.length / pieceLength + 1];for (int i = 0; i < nums.length; i++) {pieces[i / pieceLength] = pieces[i / pieceLength] + nums[i];}}public void update(int index, int val) {pieces[index / pieceLength] += (val-nums[index]);nums[index] = val;}public int sumRange(int left, int right) {int piece1 = left / pieceLength;int piece2 = right / pieceLength;int sum1 = 0, sum2 = 0, sum3 = 0;if (piece1 == piece2) {for (int i = left; i <= right; i++) {sum1 += nums[i];}} else {for (int i = left; i < pieceLength * (piece1+1); i++) {sum1 += nums[i];}for (int i = pieceLength * piece2; i <= right; i++) {sum3 += nums[i];}for (int i = piece1 + 1; i < piece2; i++) {sum2 += pieces[i];}}int sum = sum1 + sum2 + sum3;return sum;}}

相关文章:

  • VIM去掉utf-8 bom头
  • QStatusBar开发详解
  • 第三十三节——组合式API生命周期
  • 使用html2canvas转换table为图片时合并单元格rowspan失效,无边框显示问题解决(React实现)
  • python+appium自动化测试如何控制App的启动和退出
  • Java排序算法之希尔排序
  • nginx服务器
  • golang学习笔记——基础02
  • 滚雪球学Java(09-3):Java中的逻辑运算符,你真的掌握了吗?
  • 20个Golang最佳实践
  • 模拟滴答声
  • 零代码编程:用ChatGPT自动合并多个Word文件
  • Tensorflow2.0:CNN、ResNet实现MNIST分类识别
  • 宝塔https403默认串站问题解决
  • 【数据结构】树与二叉树(十八):树的存储结构——Father链接结构、儿子链表链接结构
  • DOM的那些事
  • JSDuck 与 AngularJS 融合技巧
  • Nginx 通过 Lua + Redis 实现动态封禁 IP
  • React Transition Group -- Transition 组件
  • SegmentFault 技术周刊 Vol.27 - Git 学习宝典:程序员走江湖必备
  • SOFAMosn配置模型
  • Spring技术内幕笔记(2):Spring MVC 与 Web
  • 百度贴吧爬虫node+vue baidu_tieba_crawler
  • 第十八天-企业应用架构模式-基本模式
  • 关于Flux,Vuex,Redux的思考
  • 聊一聊前端的监控
  • 微信开放平台全网发布【失败】的几点排查方法
  • 一个普通的 5 年iOS开发者的自我总结,以及5年开发经历和感想!
  • Redis4.x新特性 -- 萌萌的MEMORY DOCTOR
  • 支付宝花15年解决的这个问题,顶得上做出十个支付宝 ...
  • ​​​​​​​GitLab 之 GitLab-Runner 安装,配置与问题汇总
  • ​LeetCode解法汇总2808. 使循环数组所有元素相等的最少秒数
  • ​如何在iOS手机上查看应用日志
  • ​无人机石油管道巡检方案新亮点:灵活准确又高效
  • (Python第六天)文件处理
  • (附表设计)不是我吹!超级全面的权限系统设计方案面世了
  • (五)MySQL的备份及恢复
  • (原創) X61用戶,小心你的上蓋!! (NB) (ThinkPad) (X61)
  • (转)Groupon前传:从10个月的失败作品修改,1个月找到成功
  • (转)ORM
  • (转)从零实现3D图像引擎:(8)参数化直线与3D平面函数库
  • .[hudsonL@cock.li].mkp勒索病毒数据怎么处理|数据解密恢复
  • .mkp勒索病毒解密方法|勒索病毒解决|勒索病毒恢复|数据库修复
  • .NET 4.0中使用内存映射文件实现进程通讯
  • .NET Core 控制台程序读 appsettings.json 、注依赖、配日志、设 IOptions
  • .Net CoreRabbitMQ消息存储可靠机制
  • .NET MVC第三章、三种传值方式
  • .net/c# memcached 获取所有缓存键(keys)
  • /usr/bin/env: node: No such file or directory
  • ??myeclipse+tomcat
  • @hook扩展分析
  • @LoadBalanced 和 @RefreshScope 同时使用,负载均衡失效分析
  • @RequestParam,@RequestBody和@PathVariable 区别
  • [BROADCASTING]tensor的扩散机制
  • [ccc3.0][数字钥匙] UWB配置和使用(二)