[LeetCode] 370. Range Addition 范围相加
Assume you have an array of length n initialized with all 0's and are given k update operations.
Each operation is represented as a triplet: [startIndex, endIndex, inc] which increments each element of subarray A[startIndex ... endIndex] (startIndex and endIndex inclusive) with inc.
Return the modified array after all k operations were executed.
Example:
Given:
length = 5,
updates = [
[1, 3, 2],
[2, 4, 3],
[0, 2, -2]
]
Output:
[-2, 0, 3, 5, 3]
Explanation:
Initial state:
[ 0, 0, 0, 0, 0 ] After applying operation [1, 3, 2]:
[ 0, 2, 2, 2, 0 ] After applying operation [2, 4, 3]:
[ 0, 2, 5, 5, 3 ] After applying operation [0, 2, -2]:
[-2, 0, 3, 5, 3 ]
Hint:
- Thinking of using advanced data structures? You are thinking it too complicated.
- For each update operation, do you really need to update all elements between i and j?
- Update only the first and end element is sufficient.
- The optimal time complexity is O(k + n) and uses O(1) extra space.
Credits:
Special thanks to @vinod23 for adding this problem and creating all test cases.
这道题刚添加的时候我就看到了,当时只有1个提交,0个接受,于是我赶紧做,提交成功后发现我是第一个提交成功的,哈哈,头一次做沙发啊,有点小激动~ 这道题的提示说了我们肯定不能把范围内的所有数字都更新,而是只更新开头结尾两个数字就行了,那该怎么做呢?假设我们的数组范围是 [0, n),需要更新的区间是 [start, end],更新值是 inc,那么将区间 [start, end] 中每个数字加上 inc,等同于将区间 [start, n) 内的数字都加上 inc,然后将 [end+1, n) 区间内数字都减去 inc,明白了可以这样转换之后,我们还是不能每次都更新区间内所有的值,所以需要换一种标记方式,做法就是在开头坐标 start 位置加上 inc,而在结束位置 end 加1的地方加上 -inc。就比如说需要将新区间 [1, 3] 内数字都加2,那么我们在1的位置加2,在4的位置减2,于是数组就变成了 [0, 2, 0, 0, -2]。假如就只有这一个操作,如何得到最终的结果呢,答案是建立累加和数组,变成 [0, 2, 2, 2, 0],我们发现正好等同于直接将区间 [1, 3] 内的数字都加2。进一步分析,建立累加和数组的操作实际上是表示当前的数字对之后的所有位置上的数字都有影响,那么我们在 start 位置上加了2,表示在 [start, n) 区间范围内每个数字都加了2,而实际上只有 [start, end] 区间内的数字才需要加2,为了消除这种影响,我们需要将 [end+1, n) 区间内的数字都减去2,所以才在 end+1 位置上减去了2,那么建立累加和数组的时候就相当于后面所有的数字都减去了2。需要注意的是这里 end 可能等于 n-1,则 end+1 可能会越界,所以我们初始化数组的长度为 n+1,就可以避免越界了。那么根据题目中的例子,我们可以得到一个数组,nums = {-2, 2, 3, 2, -2, -3},然后对其做累加和就是我们要求的结果 result = {-2, 0, 3, 5, 3},参见代码如下:
解法一:
class Solution {
public:
vector<int> getModifiedArray(int length, vector<vector<int>>& updates) {
vector<int> res, nums(length + , );
for (int i = ; i < updates.size(); ++i) {
nums[updates[i][]] += updates[i][];
nums[updates[i][] + ] -= updates[i][];
}
int sum = ;
for (int i = ; i < length; ++i) {
sum += nums[i];
res.push_back(sum);
}
return res;
}
};
我们可以在空间上稍稍优化下上面的代码,用 res 来代替 nums,最后把 res 中最后一个数字去掉即可,参见代码如下:
解法二:
class Solution {
public:
vector<int> getModifiedArray(int length, vector<vector<int>>& updates) {
vector<int> res(length + );
for (auto a : updates) {
res[a[]] += a[];
res[a[] + ] -= a[];
}
for (int i = ; i < res.size(); ++i) {
res[i] += res[i - ];
}
res.pop_back();
return res;
}
}
Github 同步地址:
https://github.com/grandyang/leetcode/issues/370
类似题目:
参考资料:
https://leetcode.com/problems/range-addition/
https://leetcode.com/problems/range-addition/discuss/84223/My-Simple-C%2B%2B-Solution
https://leetcode.com/problems/range-addition/discuss/84217/Java-O(K-%2B-N)time-complexity-Solution
LeetCode All in One 题目讲解汇总(持续更新中...)
[LeetCode] 370. Range Addition 范围相加的更多相关文章
- LeetCode 370. Range Addition (范围加法)$
Assume you have an array of length n initialized with all 0's and are given k update operations. Eac ...
- [LeetCode] Range Addition 范围相加
Assume you have an array of length n initialized with all 0's and are given k update operations. Eac ...
- [LeetCode] 598. Range Addition II 范围相加之二
Given an m * n matrix M initialized with all 0's and several update operations. Operations are repre ...
- LeetCode: 598 Range Addition II(easy)
题目: Given an m * n matrix M initialized with all 0's and several update operations. Operations are r ...
- 【LeetCode】370. Range Addition 解题报告(C++)
作者: 负雪明烛 id: fuxuemingzhu 个人博客:http://fuxuemingzhu.cn/ 目录 题目描述 题目大意 解题方法 只修改区间起终点 日期 题目地址:https://le ...
- LeetCode 598. Range Addition II (范围加法之二)
Given an m * n matrix M initialized with all 0's and several update operations. Operations are repre ...
- 370. Range Addition
Assume you have an array of length n initialized with all 0's and are given k update operations. Eac ...
- [LeetCode] 598. Range Addition II_Easy tag: Math
做个基本思路可以用 brute force, 但时间复杂度较高. 因为起始值都为0, 所以肯定是左上角的重合的最小的长方形就是结果, 所以我们求x, y 的最小值, 最后返回x*y. Code ...
- 598. Range Addition II 矩阵的范围叠加
[抄题]: Given an m * n matrix M initialized with all 0's and several update operations. Operations are ...
随机推荐
- LeetCode 209:最小长度的子数组 Minimum Size Subarray Sum
公众号: 爱写bug(ID:icodebugs) 作者:爱写bug 给定一个含有 n 个正整数的数组和一个正整数 s ,找出该数组中满足其和 ≥ s 的长度最小的连续子数组.如果不存在符合条件的连续子 ...
- 深圳龙华有轨电车BIM项目
本项目是“龙华有轨电车BIM+GIS运维管理平台“研发组成的内容之一,包含站台.电车.变电所等模型绘制. 龙华区有轨电车是深圳市的一条位于龙华区的有轨电车线路,项目规划了三条线路,总长51公里.试验线 ...
- python学习笔记 - socket通信
socket socket通常也称作"套接字",用于描述IP地址和端口,是一个通信链的句柄,应用程序通常通过"套接字"向网络发出请求或者应答网络请求. sock ...
- kmv 学习笔记 工具
qemu:kmv的文本管理工具,包括qemu-kvm.qemu-img libvirt:是一套免费.开源的支持Linux下主流虚拟化工具的C函数库,libvirtd是运行的守护进程的名称.包括GUI: ...
- [Docker] Win10中安装Docker并运行Nginx镜像
一.安装Docker 进入官网:https://www.docker.com/products/docker-desktop 可能需要先注册登录,很简单的. 点击 Download Desktop f ...
- c# 调用接口返回json
需要命名空间 using System.Net; using System.Net.Security using System.Security.Cryptography.X509Certificat ...
- NumPy 文件数据读写
写数据 NumPy 数组可以使用 np.save 方法保存到本地磁盘中,默认扩展名是 .npy,并且是未压缩的二进制格式. import numpy as np a = np.array([[0, 1 ...
- 腾讯WeTest&TesterHome深圳线下沙龙
腾讯官方的一站式品质开放平台「腾讯WeTest」携手知名测试社区「TesterHome」以及3家金融相关企业为我们带来的金融专场. 本次活动内容主要以金融公司的测试落地和测试技术为主,我们希望你是一个 ...
- maven 学习---使用Maven构建项目
要构建一个基于Maven的项目,打开控制台,进入到 pom.xml 文件所放的项目文件夹,并发出以下命令: mvn package 这将执行Maven的“package”阶段. Maven构建生命周期 ...
- AI 的架构与核心
AI 的架构 人工智能的架构分为三层:应用层.技术层和基础层. 应用层聚焦在人工智能和各行业各领域的结合.技术层是算法.模型和技术开发.基础层则是计算能力和数据资源. 数据收集:获取什么类型的数据,数 ...