带修改区间第k小,使用整体二分。
1 #include <iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<algorithm> 5 #define lowbit(x) (x&-(x)) 6 using namespace std; 7 #define MAXN 100005 8 struct node 9 { 10 int tp,pos,val,ed,cur,addr; 11 }que[MAXN],q1[MAXN],q2[MAXN]; 12 struct optnode 13 { 14 int opt,pos1,pos2,val; 15 }opts[MAXN]; 16 int head,tail,cnt; 17 int ans[MAXN]; 18 int n,nn,num[MAXN],q,jump[MAXN],realval[MAXN]; 19 int maxz; 20 char opt[3]; 21 int tmp[MAXN]; 22 struct lsh 23 { 24 int val,id; 25 bool operator <(lsh &t)const 26 { 27 return val<t.val; 28 } 29 }num2[MAXN]; 30 int tree[MAXN]; 31 void init(int x) 32 { 33 maxz=0; 34 for(int i=1;i<=x;i++) 35 num2[i].val=num[i],num2[i].id=i; 36 sort(num2+1,num2+x+1); 37 for(int i=1;i<=x;i++) 38 { 39 if(num2[i].val!=num2[i-1].val) 40 ++maxz,realval[maxz]=num2[i].val; 41 num[num2[i].id]=maxz; 42 43 } 44 } 45 void add(int pos,int val) 46 { 47 while(pos<=n) 48 {tree[pos]+=val; 49 pos+=lowbit(pos); 50 } 51 } 52 int getsum(int pos) 53 { 54 int tmp=0; 55 while(pos) 56 { 57 tmp+=tree[pos]; 58 pos-=lowbit(pos); 59 } 60 return tmp; 61 } 62 void divide(int l,int r,int head,int tail) 63 { 64 if(head>tail)return; 65 if(l==r) 66 { 67 for(int i=head;i<=tail;i++) 68 { 69 if(que[i].tp==3) 70 ans[que[i].addr]=l; 71 } 72 return; 73 } 74 int mid=(l+r)/2; 75 for(int i=head;i<=tail;i++) 76 { 77 if(que[i].tp==1)if(num[que[i].val]<=mid)add(que[i].pos,1); 78 if(que[i].tp==2)if(num[que[i].val]<=mid)add(que[i].pos,-1); 79 if(que[i].tp==3) 80 tmp[i]=getsum(que[i].ed)-getsum(que[i].pos-1); 81 } 82 for(int i=head;i<=tail;i++) 83 {if(que[i].tp==1)if(num[que[i].val]<=mid)add(que[i].pos,-1); 84 if(que[i].tp==2)if(num[que[i].val]<=mid)add(que[i].pos,1); 85 } 86 87 int l1=0,r1=0; 88 for(int i=head;i<=tail;i++) 89 { 90 if(que[i].tp==3) 91 { 92 if(que[i].cur+tmp[i]>=que[i].val) 93 q1[l1++]=que[i]; 94 else 95 { 96 que[i].cur+=tmp[i]; 97 q2[r1++]=que[i]; 98 } 99 } 100 else 101 { 102 if(num[que[i].val]<=mid) 103 q1[l1++]=que[i]; 104 else q2[r1++]=que[i]; 105 } 106 } 107 for(int i=0;i<l1;i++)que[head+i]=q1[i]; 108 for(int i=0;i<r1;i++)que[head+l1+i]=q2[i]; 109 divide(l,mid,head,head+l1-1); 110 divide(mid+1,r,head+l1,tail); 111 } 112 113 int main() 114 { 115 int t1,t2,t3; 116 scanf("%d%d",&n,&q); 117 for(int i=1;i<=n;i++)scanf("%d",&num[i]),jump[i]=i; 118 int nn=n; 119 for(int i=1;i<=n;i++) 120 que[++tail].pos=i,que[tail].tp=1,que[tail].val=i; 121 for(int i=1;i<=q;i++) 122 { 123 scanf("%s",opt); 124 if(opt[0]=='Q') 125 { 126 scanf("%d %d %d",&t1,&t2,&t3); 127 que[++tail].tp=3,que[tail].pos=t1,que[tail].ed=t2,que[tail].val=t3; 128 que[tail].addr=cnt++; 129 } 130 else{ 131 scanf("%d%d",&t1,&t2); 132 num[++nn]=t2; 133 que[++tail].tp=2,que[tail].pos=t1,que[tail].val=jump[t1]; 134 que[++tail].tp=1,que[tail].pos=t1,que[tail].val=nn; 135 jump[t1]=nn; 136 } 137 } 138 init(nn); 139 divide(1,maxz,1,tail); 140 for(int i=0;i<cnt;i++) 141 printf("%d ",realval[ans[i]]); 142 return 0; 143 }