1. 程式人生 > 實用技巧 >AcWing242一個簡單的整數問題1(差分+樹狀陣列)

AcWing242一個簡單的整數問題1(差分+樹狀陣列)

題目地址https://www.acwing.com/problem/content/248/

題目描述

給定長度為N的數列A,然後輸入M行操作指令。

第一類指令形如“C l r d”,表示把數列中第l~r個數都加d。

第二類指令形如“Q X”,表示詢問數列中第x個數的值。

對於每個詢問,輸出一個整數表示答案。

輸入格式

第一行包含兩個整數N和M。

第二行包含N個整數A[i]。

接下來M行表示M條指令,每條指令的格式如題目描述所示。

輸出格式

對於每個詢問,輸出一個整數表示答案。

每個答案佔一行。

資料範圍

1N,M1e5


|d|10000,
|A[i]|1000000000

題解:樹狀陣列可以額解決的是單點修改和區間求和問題。這道題是區間修改和單點求值。那麼就需要和差分陣列來一起進行。差分陣列是在原先的陣列a的基礎上進行差分的,差分陣列b[i]=a[i]-a[i]-1,所以區間[l,r]修改就相當於b[l]+=d,b[r+1]-=d,單點求值就是對差分陣列進行字首和求值

AC程式碼

#include<iostream>
using namespace std;
const int N=1e5+10;
#define ll long long int
#define lowbit(x)  (x&-(x))
ll c[N]
={0},n,m,a[N]={0}; void add(int x,ll d){ while(x<=n){ c[x]+=d; x+=lowbit(x); } } ll sum(int x){ ll sum=0; while(x>0){ sum+=c[x]; x-=lowbit(x); } return sum; } int main(){ cin>>n>>m; ll now=0,x; for(int i=1;i<=n;i++){ cin
>>x; a[i]=x-now; now=x; } for(int i=1;i<=n;i++) add(i,a[i]); char ch; ll l,r,d; while(m--){ cin>>ch; if(ch=='C'){ cin>>l>>r>>d; add(l,d); add(r+1,-d); } else { cin>>x; cout<<sum(x)<<endl; } } return 0; }

寫於:202/8/26 13:03