主席树
如果我们每添加一个元素都需要记住这个权值线段树的状态,以便于我们对历史的操作,那么如果只使用权值线段树,则我们需要n个权值线段树同时保存状态,对于非常多的元素,我们就需要保存非常多的权值线段树,这样做空间一定会爆炸,而主席树提供了这一功能。
板子
#include<bits/stdc++.h>
using namespace std;
const int N=1e4+5;
struct node
{
int s,l,r;
}tr[N*20];
int root[N],idx;//root[x] 根节点的信息,idx 节点编号
//int &x 是传引用,给tr[x].l,tr[x].r赋值
void build(int &x,int l,int r)
{
x=++idx;
if(l==r)
return ;
int mid=(l+r)/2;
build(tr[x].l,l,mid);
build(tr[x].r,mid+1,r);
}
void insert(int x,int &y,int l,int r,int v)//x原先版本,y新版本
{
y=++idx;
tr[y]=tr[x];
tr[y].s++;
if(l==r)
return ;
int mid=(l+r)/2;
if(v<=mid)
insert(tr[x].l,tr[y].l,l,mid,v);
else
insert(tr[x].r,tr[y].r,mid+1,r,v);
}
/*
for(int i=1;i<=n;i++)
insert(root[i-1],root[i],1,n,a[i]);
*/
//查询[l,r]中第k小
long long query(int x,int y,int l,int r,int k)//x l-1版本,y r版本
{
if(l==r) return l;
int mid=(l+r)/2;
int s=tr[tr[x].l].s-tr[tr[y].l].s;
if(k<=s)
return query(tr[x].l,tr[y].l,l,mid,k);
else
return query(tr[x].r,tr[y].r,mid+1,l,k);
}
/*
cin>>l>>r>>k;
query(l-1,r,1,n,k);
*/
//离散化 可见权值线段树
int main()
{
return 0;
}
本文来自博客园,作者:流氓兔LMT,转载请注明原文链接:https://www.cnblogs.com/-include-lmt/p/18736952

浙公网安备 33010602011771号