普通算法——一维差分

一维差分

题目链接:https://www.acwing.com/problem/content/799/

题目描述:

  1. 输入一个长度为 n n n 的整数序列。
  2. 接下来输入 m m m 个操作,每个操作包含三个整数 l , r , c , l,r,c, l,r,c表示将序列中 [ l , r ] [l,r] [l,r] 之间的每个数加上 c c c
  3. 请你输出进行完所有操作后的序列。

说明:

  • 差分是前缀和的逆运算,也就是构造一个 b b b数组使 a a a数组是 b b b数组的前缀和。

  • 也就是:

    b [ 1 ] = a [ 1 ] 、 b [ 2 ] = a [ 2 ] − a [ 1 ] 、 b [ 3 ] = a [ 3 ] − a [ 2 ] 、 … 、 b [ n ] = a [ n ] − a [ n − 1 ] b[1]=a[1]、 b[2]=a[2]−a[1]、 b[3]=a[3]−a[2]、 …、 b[n]=a[n]−a[n-1] b[1]=a[1]b[2]=a[2]a[1]b[3]=a[3]a[2]b[n]=a[n]a[n1]

  • 然而差分的作用在于:动态区间增量

  1. 朴素算法: O ( n ) O(n) O(n) f o r for for循环一遍。
  2. 差分做法: O ( 1 ) O(1) O(1) b [ l ] + c b[l]+c b[l]+c b [ r + 1 ] − c b[r+1]−c b[r+1]c
#include
using namespace std;
const int N = 100010;
int n, m, a[N], l, r, c, p[N]; // p[N]为差分数组

int main(){
	cin >> n >> m;
	for (int i = 1; i <= n; i++){
		cin >> a[i];
		p[i] = a[i] - a[i-1]; // 构造差分数组
	}
	while(m--){
		cin >> l >> r >> c;
		p[l] += c;
		p[r+1] -= c; 
	}
	for (int i = 1; i <= n; i++){
		p[i] = p[i] + p[i-1];
		cout << p[i] << " ";
	}
	return 0;
}

你可能感兴趣的:(算法,算法)