可持久化线段树区间k小值求助
查看原帖
可持久化线段树区间k小值求助
822239
ncwzdlsd楼主2023/3/6 19:35

不知道哪里写挂了/kk/kk

#include <bits/stdc++.h>
using namespace std;

const int maxn=6e6+5;
int n,m,rr[maxn],s[maxn],cnt,a[maxn],b[maxn];

struct node
{
	int ls,rs,v;
}t[maxn];

int build(int l,int r)
{
	int id=++cnt;
	if(l==r) t[id].v=a[l];
	else
	{
		int mid=(l+r)/2;
		t[id].ls=build(l,mid);
		t[id].rs=build(mid+1,r);
	}
	return id;
}//记录左右儿子编号 

int neww(int x)
{
	cnt++,t[cnt]=t[x];
	return cnt;
}//新建节点 

int update(int now,int l,int r,int k) 
{
	int qwq=neww(now);
	s[qwq]=s[now]+1;
	if(l==r) return l;
	else
	{
		int mid=(l+r)/2;
		if(k<=mid) t[qwq].ls=update(t[now].ls,l,mid,k);
		else t[qwq].rs=update(t[now].rs,mid+1,r,k);
	}
	return qwq;
}

int query(int u,int v,int k,int l,int r)
{
	if(l==r) return l;
	else
	{
		int mid=(l+r)/2,x=s[t[v].ls]-s[t[u].ls];
		if(x>=k) return query(t[u].ls,t[v].ls,k,l,mid);
		else return query(t[u].rs,t[v].rs,k-x,mid+1,r);
	}
}

int main()
{
	cin>>n;
	for(int i=1;i<=n;i++) cin>>a[i],b[i]=a[i];
	sort(b+1,b+n+1);
	int qaq=unique(b+1,b+n+1)-b-1;
	rr[0]=build(1,qaq);
	for(int i=1;i<=n;i++) 
		a[i]=lower_bound(b+1,b+qaq+1,a[i])-b,rr[i]=update(rr[i-1],1,m,a[i]);
	for(int i=1;i<=m;i++)
	{
		int l,r,k;cin>>l>>r>>k;
		int ptj=query(rr[l-1],rr[r],1,qaq,k);
		cout<<b[ptj]<<endl;
	} 
	return 0;
}
2023/3/6 19:35
加载中...