差分数组
该技巧和前缀和数组一样都是用在数组上的,
前缀和数组是用来简化 任意区间的元素之和的,
差分数组是用来简化 频繁在任意区间减去某个值或者在任意区间加上某个值,最后输出最后的数组结果的
比如,给你一个数组nums[2,4,1,45,21,54,12,43]
,我需要先将[2,4]
都加3,再将[3,6]
都减1,再…..,最后输出最后的数组结果
如果没学过差分数组,那么应该是使用for循环将范围内的数都进行操作,最后输出数组,
对nums
的操作十分频繁,这样的效率十分低下
这里我们就使用差分数组来提高我们的效率
1 | int[] diff = new int[nums.length]; |
当i!=0
的时候diff[i]
代表nums[i]-nums[i-1]
的值,即当前值与前一个值的差
那有了这个差分数组,我们怎么将数组还原呢?
1 | int[] res = new int[diff.length]; |
diff
的还原是先new一个新的数组来存放最后的结果,对于0之后的元素,res[i]
等于前一个元素加上当前索引的diff
如果我要将[i,j]
区间加2,那么就将diff[i]+=2;diff[j+1]-=2
即可
我将diff[i]+=2
,即达到res[i]
到最后都会被加上2的效果
我将diff[j+1]-=2
,即达到res[j+1]
之后,会将前面的加2抵消,所以j
之后的元素就不会被影响了
我们来和之前的那道前缀和数组一样,抽象出来一个类来处理数组
1 | class Diff{ |
大家可以先自己写一下
这是实现:
1 | class Diff { |
小试牛刀
接下来就要实践出真知,来看一下这道力扣题,这道题在力扣上是plus会员才可以查看,这里直接将题目简述给大家
力扣370:区间加法
1 | # 370.区间加法 |
只要懂了上面的Diff
类的写法,这题轻轻松松拿下!
代码:
1 | public int[] getModifiedArray(int[] nums, int[][] updates) { |
既然我们之前写了Diff
那么我们就可以使用它
1 | public int[] getModifiedArray1(int[] nums, int[][] updates) { |
力扣1109:航班预订统计
本质是一样的,只不过这边需要注意一下索引和编号的对应关系,
1 | class Solution { |
相信学完这些,你对差分数组的理解也比较深刻了