线段树+等差/等比

Posted cmyg

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了线段树+等差/等比相关的知识,希望对你有一定的参考价值。

 

等差:

 

https://www.luogu.org/problemnew/show/P1438

 

 1 #include <cstdio>
 2 #include <cstdlib>
 3 #include <cmath>
 4 #include <ctime>
 5 #include <cstring>
 6 #include <string>
 7 #include <map>
 8 #include <set>
 9 #include <list>
10 #include <queue>
11 #include <stack>
12 #include <vector>
13 #include <bitset>
14 #include <algorithm>
15 #include <iostream>
16 using namespace std;
17 #define ll long long
18 const int maxn=1e5+10;
19 
20 ll a[maxn<<2],u[maxn<<2],v[maxn<<2];
21 
22 void push_down(int ind,int len)
23 {
24     u[ind<<1]+=u[ind];
25     v[ind<<1]+=v[ind];
26     u[ind<<1|1]+=u[ind]+len*v[ind];
27     v[ind<<1|1]+=v[ind];
28     u[ind]=0;
29     v[ind]=0;
30 }
31 
32 void update(int ind,int l,int r,int x,int y,int k,int d)
33 {
34     if (x<=l && r<=y)
35     {
36         u[ind]+=k+d*(l-x);
37         v[ind]+=d;
38         return;
39     }
40     if (u[ind]!=0 || v[ind]!=0)
41         push_down(ind,((r-l)>>1)+1);
42     int m=(l+r)>>1;
43     if (x<=m)
44         update(ind<<1,l,m,x,y,k,d);
45     if (m<y)
46         update(ind<<1|1,m+1,r,x,y,k,d);
47 }
48 
49 ll query(int ind,int l,int r,int p)
50 {
51     if (l==p && r==p)
52         return u[ind];
53     if (u[ind]!=0 || v[ind]!=0)
54         push_down(ind,((r-l)>>1)+1);
55     int m=(l+r)>>1;
56     if (p<=m)
57         query(ind<<1,l,m,p);
58     else
59         query(ind<<1|1,m+1,r,p);
60 }
61 
62 int main()
63 {
64     int n,m,mode,x,y,p,i;
65     ll k,d;
66     scanf("%d%d",&n,&m);
67     for (i=1;i<=n;i++)
68         scanf("%lld",&a[i]);
69     while (m--)
70     {
71         scanf("%d",&mode);
72         if (mode==1)
73         {
74             scanf("%d%d%lld%lld",&x,&y,&k,&d);
75             update(1,1,n,x,y,k,d);
76         }
77         else
78         {
79             scanf("%d",&p);
80             printf("%lld
",a[p]+query(1,1,n,p));
81         }
82     }
83     return 0;
84 }
85 /*
86 5 10
87 1 2 3 4 5
88 1 2 5 1 2
89 2 5
90 1 3 4 -1 1
91 2 4
92 1 1 5 1 3
93 2 3
94 */

 

等比:

1 void push_down(int ind,int len)
2 {
3     u[ind<<1]+=u[ind];
4     v[ind<<1]+=v[ind];
5     u[ind<<1|1]+=u[ind]+pow(v[ind],len);
6     v[ind<<1|1]+=v[ind];
7     u[ind]=0;
8     v[ind]=0;
9 }

 

以上是关于线段树+等差/等比的主要内容,如果未能解决你的问题,请参考以下文章

BZOJ4373算术天才⑨与等差数列 [线段树]

BZOJ4373算术天才⑨与等差数列 线段树+set

[CodeChef - STREETTA] The Street 李超线段树

[JSOI2009]等差数列

[JSOI2009]等差数列

C++拾取——使用stl标准库生成等差等比数列的方法