[洛谷P1438] 无聊的数列
洛谷題目鏈接:無聊的數(shù)列
題目背景
無聊的YYB總喜歡搞出一些正常人無法搞出的東西。有一天,無聊的YYB想出了一道無聊的題:無聊的數(shù)列。。。(K峰:這題不是傻X題嗎)
題目描述
維護(hù)一個(gè)數(shù)列{a[i]},支持兩種操作:
1、1 L R K D:給出一個(gè)長度等于R-L+1的等差數(shù)列,首項(xiàng)為K,公差為D,并將它對(duì)應(yīng)加到a[L]~a[R]的每一個(gè)數(shù)上。即:令a[L]=a[L]+K,a[L+1]=a[L+1]+K+D,
a[L+2]=a[L+2]+K+2D……a[R]=a[R]+K+(R-L)D。
2、2 P:詢問序列的第P個(gè)數(shù)的值a[P]。
輸入輸出格式
輸入格式:
第一行兩個(gè)整數(shù)數(shù)n,m,表示數(shù)列長度和操作個(gè)數(shù)。
第二行n個(gè)整數(shù),第i個(gè)數(shù)表示a[i](i=1,2,3…,n)。
接下來的m行,表示m個(gè)操作,有兩種形式:
1 L R K D
2 P 字母意義見描述(L≤R)。
輸出格式:
對(duì)于每個(gè)詢問,輸出答案,每個(gè)答案占一行。
輸入輸出樣例
輸入樣例#1: 復(fù)制
5 2
1 2 3 4 5
1 2 4 1 2
2 3
輸出樣例#1: 復(fù)制
6
說明
數(shù)據(jù)規(guī)模:
0≤n,m≤100000
|a[i]|,|K|,|D|≤200
分析一下題意:給出一個(gè)長度為n的序列,m次操作,單點(diǎn)修改和區(qū)間修改,單點(diǎn)查詢.
做法:
- 差分記錄修改
- 線段樹維護(hù)區(qū)間
- 查詢時(shí)輸出修改的值加原值
下面貼一下代碼:
#include<bits/stdc++.h> #define ll(x) (x<<1) #define rr(x) (x<<1|1) using namespace std; const int N=100000+5;int n, m, w[N];struct segment_tree{int l, r, sum, tag; }t[N*4];int gi(){int ans = 0 , f = 1; char i = getchar();while(i<'0'||i>'9'){if(i=='-')f=-1;i=getchar();}while(i>='0'&&i<='9'){ans=ans*10+i-'0';i=getchar();}return ans * f; }void up(int x){t[x].sum = t[ll(x)].sum+t[rr(x)].sum; }void build(int node,int l,int r){t[node].l = l; t[node].r = r;if(l == r) return;int mid = (l+r>>1);build(ll(node),l,mid);build(rr(node),mid+1,r);up(node); }void pushdown(int node){int ls = ll(node), rs = rr(node), tag = t[node].tag;int l = t[node].l, r = t[node].r , mid = (l+r>>1);t[ls].tag += tag; t[rs].tag += tag;t[ls].sum += tag*(mid-l+1); t[rs].sum += tag*(r-mid);t[node].tag = 0; }void updata(int node,int l,int r,int val){if(l <= t[node].l && t[node].r <= r){t[node].tag += val;t[node].sum += val*(t[node].r-t[node].l+1);return;}if(t[node].tag) pushdown(node);int mid = (t[node].l+t[node].r>>1);if(l <= mid) updata(ll(node),l,r,val);if(mid < r) updata(rr(node),l,r,val);up(node); }int query(int node,int l,int r){if(l <= t[node].l && t[node].r <= r) return t[node].sum;if(r < t[node].l || t[node].r < l) return 0;if(t[node].tag) pushdown(node);return query(ll(node),l,r)+query(rr(node),l,r); }int main(){//freopen("data.in","r",stdin);int flag, l, r, k, d; n = gi(); m = gi();for(int i=1;i<=n;i++) w[i] = gi();build(1,1,n);while(m--){flag = gi(); l = gi();if(flag == 1){r = gi(); k = gi(); d = gi();updata(1,l+1,r,d); updata(1,l,l,k);if(r+1 <= n) updata(1,r+1,r+1,-d*(r-l)-k);//因?yàn)榻涞臅r(shí)候沒有建n+1的下標(biāo),所以特判防越界}else printf("%d\n",w[l]+query(1,1,l));}return 0; }轉(zhuǎn)載于:https://www.cnblogs.com/BCOI/p/8867637.html
總結(jié)
以上是生活随笔為你收集整理的[洛谷P1438] 无聊的数列的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 解決 centos -bash: vim
- 下一篇: bzoj2007: [Noi2010]海