水题,树状数组就行了。。。注意三种操作。。。
#include<iostream>
#include<cstring>
#include<cstdio>
#define FF(i, a, b) for(i = a; i <= b; i++)
#define FD(i, a, b) for(i = b; i >= a; i--)
#define CLR(a, b) memset(a, b, sizeof(a))
#define CPY(a, b) memcpy(a, b, sizeof(a))
#define LL __int64
using namespace std;
const int maxn = 1e5 +10;
LL n, m, c[maxn], cnt;
LL low(LL i) { return i & (-i);}
void add(LL i, LL p)
{
while(i <= n)
{
c[i] += p;
i += low(i);
}
}
LL get(LL n)
{
LL ret = 0;
while(n > 0)
{
ret += c[n];
n -= low(n);
}
return ret;
}
int main()
{
while(~scanf("%I64d%I64d", &n, &m))
{
cnt = 0;
CLR(c, 0);
LL i, x, y, z;
FF(i, 1, n)
{
scanf("%I64d", &x);
add(i, x);
}
while(m--)
{
scanf("%I64d", &x);
if(x == 1)
{
scanf("%I64d%I64d", &y, &z);
LL tmp = get(y) - get(y-1);
add(y, z-tmp-cnt);
}
else if(x == 2)
{
scanf("%I64d", &y);
cnt += y;
}
else
{
scanf("%I64d", &y);
printf("%I64d\n", get(y) - get(y-1) + cnt);
}
}
}
return 0;
}