差分是一種支持區間大量修改的操作,是一種很巧妙的思想。 差分序列的前綴和序列就是原序列。B[i]=A[i]-A[i-1]
假如有一個年級考試,批卷時發現有一題全體改錯了,需要全部加x分。按照樸素暴力的思想,就是將以前所有的批了的試卷全部再拿出來,再一張張的加分。這當然過於的慢,所以便有了差分的這種算法:說白了,就是將一整個考場的試卷封面上寫上“加x分”,這樣便省去了許多功夫。
題目鏈接
題意:
給你n個數, 組成一個1~n的數組,且數組的元素互不重複。m次詢問區間,並計算區間元素的和,問如何詢問使得元素的和最大。
題解:
將題目轉化爲求出每個點的出現次數。
使用差分和前綴和的思想,差分求出區間的權值,再前綴和求出每個點出現的個數。
for(int i = 1;i <= m;i++) {
int l = cin.nextInt();
int r = cin.nextInt();
d[l]++;
d[r + 1]--;
}
for(int i = 1;i <= n;i++)
d[i] += d[i - 1];
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedList;
import java.util.HashMap;
import java.util.HashMap;
import java.util.Queue;
import java.util.Scanner;
import java.util.Set;
import java.util.TreeSet;
import java.util.Vector;
public class Main {
public static void main(String[] args) {
Scanner cin = new Scanner(System.in);
int n = cin.nextInt();
int m = cin.nextInt();
long d[] = new long[200005];
for(int i = 1;i <= m;i++) {
int l = cin.nextInt();
int r = cin.nextInt();
d[l]++;
d[r + 1]--;
}
for(int i = 1;i <= n;i++)
d[i] += d[i - 1];
Arrays.sort(d, 1, n + 1);
long ans = 0;
for(int i = 1;i <= n;i++)
ans += i * d[i];
System.out.println(ans);
}
}