二阶差分数组
题目描述
小明在练习绝世武功, nn 个练功桩排成一排,一开始每个桩的损伤为 00。
接下来小明会练习 mm 种绝世武功,每种武功都会对 [l, r][l,r] 区间分别造成 [s,e][s,e] 的伤害。
这个伤害是一个等差序列。例如 l = 1, r = 4, s = 2, e = 8l=1,r=4,s=2,e=8 ,则会对 1-41−4 号练功桩造成2, 4, 6, 82,4,6,8 点损伤。
小明想让你统计一下所有练功桩的损伤的和。
输入描述
第一行输入 n, mn,m,代表练功桩的数量和绝世武功的种类数。
接下来 mm 行输入 44 个整数 l, r, s, el,r,s,e 。
1 \leq n \leq 10^7 , 1\leq m \leq 3 \times 10 ^ 5 , 1\leq l, r \leq n1≤n≤107,1≤m≤3×105,1≤l,r≤n
输出描述
输出一个整数代表所有练功桩的损伤和, 题目保证所有输入输出都在 [0, 9 \times 10^{18}][0,9×1018]
输入输出样例
示例 1
输入
6 2
1 5 2 10
2 4 1 1
输出
33
运行限制
- 最大运行时间:1s
- 最大运行内存: 512M
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.StreamTokenizer;
public class Main {
public static void main(String[] args) throws IOException {
int n,m;
StreamTokenizer in = new StreamTokenizer(new BufferedReader(new InputStreamReader(System.in)));
in.nextToken();
n = (int) in.nval;
in.nextToken();
m = (int) in.nval;
long[] a = new long[10000010];
long[] b = new long[10000010];
long[] c = new long[10000010];
int l,r,s,e,d;
for(int i=1; i<=m; i++) {
in.nextToken();
l = (int) in.nval;
in.nextToken();
r = (int) in.nval;
in.nextToken();
s = (int) in.nval;
in.nextToken();
e = (int) in.nval;
d = (e-s) / (r-l);//公差
c[l] = c[l]+s;
c[l+1] = c[l+1]+d-s;
c[r+1] = c[r+1]-d-e;
c[r+2] = c[r+2]+e;
}
long sum = 0;
for(int i=1; i<=n; i++) {
b[i] = c[i] + b[i-1];
a[i] = b[i] + a[i-1];
sum +=a[i];
}
System.out.println(sum);
}
}