Pagini recente » Cod sursa (job #2311564) | Cod sursa (job #2849095) | Cod sursa (job #442854) | Cod sursa (job #606969) | Cod sursa (job #2142258)
#include <fstream>
#define MAX 100005
using namespace std;
ifstream fi("aib.in");
ofstream fo("aib.out");
int n,m;
int A[MAX];
inline int lst(int x)
{
return (x^(x-1))&x;
}
void build()
{
for (int i=1; i<=n; i++)
{
/// determinam A[i]
int x=i-1;
while (x>i-lst(i))
{
A[i]+=A[x];
x-=lst(x);
}
}
}
void update(int poz,int val)
{
int x=poz;
while (x<=n)
{
A[x]+=val;
x+=lst(x);
}
}
int sum(int poz)
{
/// suma din 1...poz
int x=poz,rez=0;
while (x>0)
{
rez+=A[x];
x-=lst(x);
}
return rez;
}
int pozitie(int val)
{
/// pe ce pozitie avem suma de la 1 la k = val
int x=0,l,sum;
while ((1<<(x+1))<=n && A[1<<x]<=val)
x++;
if (A[1<<x]>val && x>=0)
x--;
if (x<0)
return -1;
l=1<<x; /// lungimea curenta
x=1<<x; /// pozitia pe care ne aflam
sum=A[x];
while (sum<val && x<=n && l)
{
l>>=1;
while (x+l>n)
l>>=1;
while (l>=1 && A[x+l]+sum>val)
l>>=1;
if (!l)
break;
sum+=A[x+l];
x+=l;
}
if (sum==val)
return x;
return -1;
}
int main()
{
fi>>n>>m;
for (int i=1; i<=n; i++)
{
fi>>A[i];
}
build();
//for (int i=1; i<=n; i++)
//fo<<"suma de la "<<i-lst[i]+1<<" la "<<i<<": "<<A[i]<<"\n";
while (m--)
{
int op,a,b;
fi>>op;
if (op==0)
{
fi>>a>>b;
update(a,b);
}
else if (op==1)
{
fi>>a>>b;
fo<<sum(b)-sum(a-1)<<"\n";
}
else
{
fi>>a;
fo<<pozitie(a)<<"\n";
}
}
return 0;
}