主席树 模板

#include<bits/stdc++.h>
using namespace std;
#define N 100010
#define M 2000010
int root[N],R[M],L[M],s[M],m,x,y,n,k,a[N],cnt;

void update(int &A,int &B,int l,int r,int k){
    B=++cnt;
    s[B]=s[A]+1;
    if(l==r)return;
    int mid=(l+r)/2;
    if(k<=mid)update(L[A],L[B],l,mid,k);
    else update(R[A],R[B],mid+1,r,k);
    if(!L[B])L[B]=L[A];
    if(!R[B])R[B]=R[A];
}

int find(int A,int B,int l,int r){
    if(l==r)return l;
    int mid=(l+r)/2;
    if(s[R[B]]-s[R[A]]>=k)return find(R[A],R[B],mid+1,r);
    else{
        k-=s[R[B]]-s[R[A]];
        return find(L[A],L[B],l,mid);
    }
}

int main(){
    scanf("%d%d",&n,&m);
    for(int i=1;i<=n;i++)scanf("%d",&a[i]);
    for(int i=1;i<=n;i++)update(root[i-1],root[i],1,100000,a[i]);
    while(m--){
        scanf("%d%d%d",&x,&y,&k);
        cout<<find(root[x-1],root[y],1,100000)<<endl;
    }
    return 0;
}

时间: 2024-10-27 13:14:14

主席树 模板的相关文章

【POJ 2104】 K-th Number 主席树模板题

达神主席树讲解传送门:http://blog.csdn.net/dad3zz/article/details/50638026 2016-02-23:真的是模板题诶,主席树模板水过.今天新校网不好,没有评测,但我立下flag这个代码一定能A.我的同学在自习课上考语文,然而机房党都跑到机房来避难了\(^o^)/~ #include<cstdio> #include<cstring> #include<algorithm> #define for1(i,a,n) for(i

【Luogu】P3384主席树模板(主席树查询K小数)

YEAH!我也是一个AC主席树模板的人了! 其实是个半吊子 我将尽量详细的讲出我的想法. 主席树太难,我们先搞普通线段树好了 普通线段树怎么做?我的想法是查询K次最小值,每次查完把查的数改成INF,查完再改回来... MDZZ 于是就有了主席树. 先不考虑主席树,我们来考虑一个奇特的线段树. 一般的线段树,数列位置是下标,而把数列维护值作为线段树中存的元素. 那我们如果反过来,把数列元素当做线段树的下标...??? 比如说数列[4 2 3 1] 如果线段树的下标是1.2.3.4......? 那

【BZOJ 1901】【Zju 2112】 Dynamic Rankings 动态K值 树状数组套主席树模板题

达神题解传送门:http://blog.csdn.net/dad3zz/article/details/50638360 说一下我对这个模板的理解: 看到这个方法很容易不知所措,因为动态K值需要套树状数组,而我一开始根本不知道该怎么套,, 学习吧,,, 然后我自己脑补如果不套会如何?后来想到是查询O(logn),修改是O(nlogn),很明显修改的复杂度太大了,为了降低修改的复杂度,我们只得套上树状数组来维护前缀和使它的n的复杂度降低为logn,从而修改的复杂度变为O(log2n).但因为我们套

主席树模板

#include<cstdio> #include<algorithm> #include<cstring> using namespace std; const int M = 50006; int w[M], a[M], root[M]; struct Tree{ int ls, rs, w; } tr[M << 4] ; int tot ; void insert(int &x, int l, int r, int d){ tr[++tot]

可持久化线段树 1(主席树模板)

[模板]可持久化线段树 1(主席树)(luogu) (本人的模板) Description 题目背景 这是个非常经典的主席树入门题——静态区间第 kk 小数据已经过加强,请使用主席树.同时请注意常数优化 题目描述 如题,给定 nn 个整数构成的序列,将对于指定的闭区间查询其区间内的第 kk 小值. 输入格式 第一行包含两个正整数 n,mn,m,分别表示序列的长度和查询的个数.第二行包含 nn 个整数,表示这个序列各项的数字.接下来 mm 行每行包含三个整数 l, r, kl,r,k , 表示查询

POJ2104主席树模板题

完成新成就——B站上看了算法https://www.bilibili.com/video/av4619406/?from=search&seid=17909472848554781180#page=2 K-th Number Time Limit: 20000MS   Memory Limit: 65536K Total Submissions: 60158   Accepted: 21054 Case Time Limit: 2000MS Description You are working

2015百度之星1002 查找有序序列(RMQ+主席树模板水过)

题意:求在数列中能找到几个个长度为k 的区间,里面的 k 个数字排完序后是连续的. 思路:枚举范围,判断区间内是否有重复的数字(主席树),没有的话求区间最大-区间最小(RMQ),判断是否等于K,是的话sum++,否则continue: 主席树:原理不太懂,暂时还没能到能研究的水平,不过知道时间复杂度之类的,以后希望能用到的时候不是敲完上交了才知道超时了.... 时间复杂度 建树      O(n): 更新     O(log(n)): 查询     O(log(n)): 1 #include <

主席树模板(一)

引入 首先请求出: ? 长度为n的序列 ? m次询问全局第k小 做法: ? 画一棵(权值)线段树手动模拟,请记住此过程 之后,请思考; ? 长度为n的序列 ? m次询问区间[l, r]中第k小值 ? 值域 ±1e9 ? n≤2e5 , m≤2e5 做法: 可持久化线段树 原理 用 [1, r]建得的线段树 - [1, l-1]建得的线段树 (即把这两颗形状一样的线段树上的每个节点的权值相减), 得到的即为区间[l, r]建得的线段树, 这样之后,我们就可以求出(这棵线段树)全局第k小值,而这个值

主席树模板(区间第k小)

#include<cmath> #include<cstdio> #include<cstdlib> #include<cstring> #include<iostream> #include<algorithm> #define MAXN 200010 using namespace std; int n,m,cnt; struct Tree { int l,r,sum; }T[MAXN*60]; int rank[MAXN],ro