【主席树】【bzoj 1901】: Zju2112 Dynamic Rankings

http://www.lydsy.com/JudgeOnline/problem.php?id=1901


Orz 主席!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

这主席树理解起来真tm困难,用BIT来套,就不想说什么了

开始想的动态开点,就没有离散化,结果二分的时候可能慢一点


update

今天下午想了一下,发现主席树不难嘛

空间O(nlognlogn)有点吃紧

树状数组每个点维护个前缀,把树状数组询问的点保存起来就可以了

为什么树套树的复杂度多了一个log捏,我今天才知道

可持久化线段树还有一个性质是平衡树不具备的

——每棵树的结构相同,这样就可以整体操作了


//#define _TEST _TEST
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <cmath>
#include <algorithm>
#include <map>
using namespace std;
/************************************************
Code By willinglive    Blog:http://willinglive.cf
************************************************/
#define rep(i,l,r) for(int i=l,___t=(r);i<=___t;i++)
#define per(i,r,l) for(int i=r,___t=(l);i>=___t;i--)
#define MS(arr,x) memset(arr,x,sizeof(arr))
#define LL long long
#define INE(i,u,e) for(int i=head[u];~i;i=e[i].next)
inline const int read()
{
    int r=0,k=1;char c=getchar();
    for(;c<'0'||c>'9';c=getchar())if(c=='-')k=-1;
    for(;c>='0'&&c<='9';c=getchar())r=r*10+c-'0';
    return k*r;
}
/////////////////////////////////////////////////
int n,m;
int a[10010],cnt,b[10010];
int root[10010];
map<int,int>M;
int s[10010];
/////////////////////////////////////////////////
namespace Chair
{///////////////////////////////////
int sz[4000000],tot;
int ls[4000000],rs[4000000];
void insert(int &o,int L,int R,int x,int val)
{
	if(!o) o=++tot;
	sz[o]+=val;
	if(L==R) return;
	int mid=L+R>>1;
	if(x<=mid) insert(ls[o],L,mid,x,val);
	else insert(rs[o],mid+1,R,x,val);
}
}///////////////////////////////////
namespace BIT
{///////////////////////////////////
void add(int o,int x,int val)
{
	for(;o<=n;o+=o&-o) Chair::insert(root[o],0,1000000000,x,val);
}
void query(int x,int y,int k)
{
	using namespace Chair;
	int i,l=0,r=1000000000,mid;
	int top=0,topr;
	for(i=y;i;i-=i&-i) s[++top]=root[i]; //[1,topr]
	topr=top;
	for(i=x-1;i;i-=i&-i) s[++top]=root[i]; //[topr+1,top]
	while(l<r)
	{
		mid=l+r>>1;
		int res=0;
		rep(i,1,topr) res+=sz[ls[s[i]]];
		rep(i,topr+1,top) res-=sz[ls[s[i]]];
		if(res>=k)
		{
			r=mid;
			rep(i,1,top) s[i]=ls[s[i]];
		}
		else
		{
			l=mid+1;
			k-=res;
			rep(i,1,top) s[i]=rs[s[i]];
		}
	}
	printf("%d\n",l);
}
}///////////////////////////////////
/////////////////////////////////////////////////
void input()
{
    n=read(); m=read();
    rep(i,1,n) a[i]=read();
}
void solve()
{
	using namespace BIT;
	char op[3];int l,r,k;
    rep(i,1,n) add(i,a[i],1);
    rep(i,1,m)
    {
    	scanf("%s",op); l=read(); r=read();
    	if(op[0]=='C')
    	{
    		add(l,a[l],-1);
    		add(l,r,1);
    		a[l]=r;
    	}
    	else
    	{
    		k=read();
    		query(l,r,k);
    	}
    }
}
/////////////////////////////////////////////////
int main()
{
    #ifndef _TEST
    freopen("std.in","r",stdin); freopen("std.out","w",stdout);
    #endif
    input(),solve();
    return 0;
}


发布了221 篇原创文章 · 获赞 2 · 访问量 22万+
展开阅读全文

没有更多推荐了,返回首页

©️2019 CSDN 皮肤主题: 编程工作室 设计师: CSDN官方博客

分享到微信朋友圈

×

扫一扫,手机浏览