ZOJ 2112
带修改的区间第k小只用比静态的多加一个删除操作即可
#include <bits/stdc++.h>
using namespace std;
const int inf=1e9+7;
const int maxn=220000;
struct node
{
int l,r,k,val,cur;
int id,kind;
}q[maxn],q1[maxn],q2[maxn];
int bit[maxn];
int ans[maxn];
int book[maxn];
int n,m,a[maxn];
int lowbit(int x)
{
return x&(-x);
}
void updata(int pos,int val)
{
for(int i=pos;i<=n;i+=lowbit(i))
{
bit[i] += val;
}
}
int query(int pos)
{
int ans=0;
for(int i=pos;i>0;i-=lowbit(i))
{
ans+=bit[i];
}
return ans;
}
void cdq(int begin,int end,int l,int r)
{
if(begin > end) return;
if(l==r)
{
for(int i=begin;i<=end;++i)
{
if(q[i].kind==3) ans[q[i].id] = l;
}
return;
}
int mid=(l+r)>>1;
for(int i=begin;i<=end;++i)
{
if(q[i].kind==1 && q[i].val <= mid) updata(q[i].id,1);
else if(q[i].kind==2 && q[i].val <=mid) updata(q[i].id,-1);
else book[i] = query(q[i].r)-query( q[i].l -1);
}
for(int i=begin;i<=end;++i)
{
if(q[i].kind==1 && q[i].val <=mid) updata(q[i].id,-1);
else if(q[i].kind==2 && q[i].val<=mid) updata(q[i].id,1);
}
int num1=0 , num2=0 ;
for(int i=begin;i<=end;++i)
{
if(q[i].kind==3)
{
if(q[i].cur+book[i]>q[i].k-1)
{
q1[++num1] = q[i];
}
else
{
q[i].cur+=book[i];
q2[++num2] = q[i];
}
}
else
{
if(q[i].val<=mid) q1[++num1]=q[i];
else q2[++num2] = q[i];
}
}
for(int i=1;i<=num1;++i) q[begin+i-1] = q1[i];
for(int i=1;i<=num2;++i) q[begin+num1+i-1] = q2[i];
cdq(begin,begin+num1-1, l,mid);
cdq(begin+num1 ,end, mid+1,r);
}
int main()
{
int T;
scanf("%d",&T);
while(T--)
{
memset(bit,0,sizeof(bit));
memset(book,0,sizeof(book));
memset(a,0,sizeof(a));
memset(q,0,sizeof(q));
scanf("%d%d",&n,&m);
int tot=0;
int cnt=0;
for(int i=1;i<=n;++i)
{
scanf("%d",&a[i]);
q[++tot].cur=0; q[tot].id=i; q[tot].kind=1;
q[tot].val=a[i];
}
char s[50];
int x=0,y=0;
for(int i=1;i<=m;++i)
{
scanf("%s",s);
if(s[0]=='Q')
{
q[++tot].kind=3; q[tot].id=(++cnt); q[tot].val=0; q[tot].cur=0;
scanf("%d%d%d",&q[tot].l,&q[tot].r,&q[tot].k);
}
else
{
scanf("%d%d",&x,&y);
q[++tot].kind = 2; q[tot].id = x; q[tot].val=a[x]; q[tot].cur=0;
q[++tot].kind = 1; q[tot].id = x; q[tot].val=y; q[tot].cur=0;
a[x]=y;
}
}
cdq(1,tot,0,inf);
for(int i=1;i<=cnt;++i)
{
printf("%d\n",ans[i]);
}
}
return 0;
}