开启掘金成长之旅!这是我参与「掘金日新计划 · 12 月更文挑战」的第1天,点击查看活动详情
定义
一般差分数组用在,你需要在数组的某一个区间内进行频繁的增减操作
一般题目意思类似于:
给你一个数组
nums,然后又要求给区间nums[2..6]全部加 1,再给nums[3..9]全部减 3,再给nums[0..4]全部加 2,再给…,最后要你输出当前数组
这种题目就很明显使用差分数组
概念
-
他的长度和原数组的长度是一致的
-
diff[i] = nums[i]- nums[i-1]其实就是:后一个减去前一个的和
-
我们可以利用差分数组求出原数组
nums[i] = nums[i-1]+diff[i]
举例
现在给你一个数组
[8,5,9,6,1]希望你在将下标
[1~3]的值全部加3
- 那么按照前面说的,首先我们构造出了一个差分数组
- 然后因为,我们需要将[1...3]的值全部加3
- 那么我们就可以将
diff[1] += 3 - 让
diff[4] -= 3 - 这样就可以实现只在
[1~3]实现加3
疑惑:
你可能会对diff[i] += inc,对diff[j+1] -= inc感觉疑惑
我的理解就是,你可以将它理解为一个链
我们知道nums[i] = diff[i]+num[i-1]
- 那么首先
diff[1]加了3以后,很显然,num[1]也就自然而然的加3 - 那么我们计算
nums[2]的时候,nums[2] = diff[2]+ nums[1], - 虽然我的
diff[2]没有进行加3,但是因为nums[1]加了3,所以,这个nums[2]也就加3 - 就这样一直到了
nums[3] - 那么为什么我们需要将
diff[j+1] -= inc呢? - 因为题目要求,只能让
[1,3]加3 - 那为什么设置
diff[j+1]而不是diff[j] - 因为我们
nums[j]也是需要加3的 nums[j+1] = diff[j+1] +nums[j],j+1减3,以后,才可以使后面的都变为原来的值
例题
区间加法
题解:
这道就是一个很明显的差分数组题目,但是,略有不同的是,他没有用提供我们原来数组,可是题目也说了,原来数组就是,长度为len的,值为0的数组,那么很显然,他的差分数组也是,长度为len,值全都为0的数组,我们只需要对数组进行操作即可
代码:
var getModifiedArray = function(length: number, update: number[][]){
// 对一个数组进行频繁操作(进行增减,那么我们就可以使用差分数组)
// 差分数组:数组长度和原数组长度一样
// diff[i] = nums[i]-nums[i-1]
// nums[i] = diff[i]+nums[i-1]
// 首选先构造差分数组
let diff = new Array(length).fill(0);
// console.log(diff)
// 现在进行操作
for (let value of update) {
let firstIndex = value[0];
let lastIndex = value[1];
let inc = value[2];
diff[firstIndex] += inc;
if (lastIndex + 1 < diff.length) {
diff[lastIndex + 1] -= inc;
}
}
return getRes(diff);
}
// 根据差分数组求除原料数组
var getRes = function (diff:number[]) {
// nums[i] = diff[i]+nums[i-1]
let len = diff.length;
let nums = new Array(len).fill(0);
nums[0] = diff[0]
for (let i = 1; i < diff.length; i++){
nums[i] = diff[i]+nums[i-1]
}
return nums
}
航班预定统计
链接:1109. 航班预订统计 - 力扣(LeetCode)
题解:
- 其实这道题也是一个差分数组题,其实和上面这题非常类似
- 唯一的不同就是,下标是从
1开始的 - 但是数组的下标是从
0开始的 - 所以我们需要将下标减
1
代码:
function corpFlightBookings(bookings: number[][], n: number): number[] {
// 其实他也是一个差分数组,和370那道题目类似
// 设置差分数组
let diff = new Array(n).fill(0);
// 差分数组往里面添加值
for(let value of bookings){
let firstIndex= value[0]-1;
let lastIndex = value[1]-1;
let count = value[2];
// 往差分数组里面添加值
diff[firstIndex] += count;
if(lastIndex + 1 < n){
diff[lastIndex+1] -= count;
}
}
console.log(diff)
return getRes(diff)
};
// 通过差分数组,求出原来的数组
var getRes = function(diff:number[]){
// 新建原数组
let len = diff.length;
let nums = new Array(len).fill(0)
// 对数组进行变化
nums[0] = diff[0];
for(let i = 1;i<len;i++){
nums[i] = diff[i]+nums[i-1]
}
return nums
}