Meaning of the questions:
To give you an array, q times ask, ask you each time [l, r] and p distance within the range from k-th largest element of p, forcing online
Ideas:
President tree extract in the segment tree weights [l, r], and then half of the distance from mid p
The weight ask segment tree [p-mid, p + mid] number of values so that it is just greater than equal to k
Code:
#include<iostream> #include<cstdio> #include<algorithm> #include<cmath> #include<cstring> #include<string> #include<stack> #include<queue> #include<deque> #include<set> #include<vector> #include<map> #define fst first #define sc second #define pb push_back #define mem(a,b) memset(a,b,sizeof(a)) #define lson l,mid,root<<1 #define rson mid+1,r,root<<1|1 #define lc root<<1 #define rc root<<1|1 using namespace std; typedef double db; typedef long double ldb; typedef long long ll; typedef unsigned long long ull; typedef pair<int,int> PI; typedef pair<ll,ll> PLL; const db eps = 1e-6; const int mod = 1e9+7; const int maxn = 2e7+2e6+100; const int maxm = 4e6+100; const int inf = 0x3f3f3f3f; const db pi = acos(-1.0); int ls[maxn],rs[maxn],dat[maxn]; int tot; int n,q; int a[maxm]; int root[maxm]; int t; int insert(int now, int l, int r, int x, int val){ int p = ++tot; ls[p]=ls[now];rs[p]=rs[now];dat[p]=dat[now]; if(l==r){ dat[p]+=val; return p; } int mid = (l+r)>>1; if(x<=mid)ls[p]=insert(ls[now],l,mid,x,val); else rs[p]=insert(rs[now],mid+1,r,x,val); dat[p]=dat[ls[p]]+dat[rs[p]]; return p; } int ask(int lst, int now, int l, int r, int L, int R){ //printf("%d %d %d %d %d %d\n",lst,now,l,r,L,R); int mid = (l+r)>>1; int ans = 0; if(L<=l&&r<=R)return dat[now]-dat[lst]; if(L<=mid)ans+=ask(ls[lst],ls[now],l,mid,L,R); if(mid<R)ans+=ask(rs[lst],rs[now],mid+1,r,L,R); return ans; } int K,p; bool cmp(int a, int b){ return abs(a-p)<abs(b-p); } int main(){ scanf("%d", &t); while(t--){ int lstans = 0; mem(dat,0); tot=0; scanf("%d %d", &n, &q); for(int i = 1; i <= n; i++){ scanf("%d", &a[i]); root[i]=insert(root[i-1],1,1000000,a[i],1); } while(q--){ int l, r; scanf("%d %d %d %d", &l, &r, &p, &K); l^=lstans; r^=lstans; p^=lstans; K^=lstans; int ans; int L = 0; int R = 1000000; while(L<=R){ int mid = (L+R)>>1; int res = ask(root[l-1],root[r],1,1000000,max(1,p-mid),min(1000000,p+mid)); if(res>=K){ ans=mid; R=mid-1; } else L=mid+1; } lstans=ans; printf("%d\n",ans); } } return 0; } /* 1 5 2 31 2 5 45 4 1 5 5 1 2 5 3 2 */