HDU5919:Sequence II

题面

Vjudge

Sol

给一个数列,有m个询问,每次问数列[l,r]区间中所有数的第一次出现的位置的中位数是多少,强制在线

主席树
询问区间内不同的数的个数
树上二分找到那个中位数

# include <bits/stdc++.h>
# define RG register
# define IL inline
# define Fill(a, b) memset(a, b, sizeof(a))
using namespace std;
typedef long long ll;
const int _(2e5 + 5);
const int __(8e6);

IL int Input(){
    RG int x = 0, z = 1; RG char c = getchar();
    for(; c < '0' || c > '9'; c = getchar()) z = c == '-' ? -1 : 1;
    for(; c >= '0' && c <= '9'; c = getchar()) x = (x << 1) + (x << 3) + (c ^ 48);
    return x * z;
}

int n, m, rt[_], tot, o[_], len, a[_], vis[_];
struct HJT{
    int ls, rs, sz;
} T[__];

IL void Modify(RG int &x, RG int l, RG int r, RG int p, RG int v){
    T[++tot] = T[x], T[x = tot].sz += v;
    if(l == r) return;
    RG int mid = (l + r) >> 1;
    if(p <= mid) Modify(T[x].ls, l, mid, p, v);
    else Modify(T[x].rs, mid + 1, r, p, v);
}

IL int Query(RG int x, RG int l, RG int r, RG int L, RG int R){
    if(!x) return 0;
    if(L <= l && R >= r) return T[x].sz;
    RG int mid = (l + r) >> 1, ret = 0;
    if(L <= mid) ret = Query(T[x].ls, l, mid, L, R);
    if(R > mid) ret += Query(T[x].rs, mid + 1, r, L, R);
    return ret;
}

IL int Calc(RG int x, RG int l, RG int r, RG int k){
    if(l == r) return l;
    RG int mid = (l + r) >> 1, s = T[T[x].ls].sz;
    if(k <= s) return Calc(T[x].ls, l, mid, k);
    return Calc(T[x].rs, mid + 1, r, k - s);
}

int main(RG int argc, RG char* argv[]){
    for(RG int t = Input(), Case = 1; Case <= t; ++Case){
        Fill(T, 0), Fill(rt, 0), Fill(vis, 0), tot = 0;
        n = Input(), m = Input();
        for(RG int i = 1; i <= n; ++i) o[i] = a[i] = Input();
        sort(o + 1, o + n + 1), len = unique(o + 1, o + n + 1) - o - 1;
        for(RG int i = n; i; --i){
            a[i] = lower_bound(o + 1, o + len + 1, a[i]) - o;
            rt[i] = rt[i + 1];
            if(!vis[a[i]]) vis[a[i]] = i, Modify(rt[i], 1, n, i, 1);
            else{
                Modify(rt[i], 1, n, vis[a[i]], -1);
                vis[a[i]] = i;
                Modify(rt[i], 1, n, i, 1);
            }
        }
        printf("Case #%d:", Case);
        for(RG int i = 1, ans = 0; i <= m; ++i){
            RG int l = Input(), r = Input(), ql, qr, num;
            ql = min((l + ans) % n + 1, (r + ans) % n + 1);
            qr = max((l + ans) % n + 1, (r + ans) % n + 1);
            num = Query(rt[ql], 1, n, ql, qr);
            printf(" %d", ans = Calc(rt[ql], 1, n, (num + 1) >> 1));
        }
        puts("");
    }
    return 0;
}

原文地址:https://www.cnblogs.com/cjoieryl/p/8486214.html

时间: 2024-10-15 02:15:00

HDU5919:Sequence II的相关文章

HDU 5919 Sequence II(主席树+逆序思想)

Sequence II Time Limit: 9000/4500 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others) Total Submission(s): 1422    Accepted Submission(s): 362 Problem Description Mr. Frog has an integer sequence of length n, which can be denoted as a1,a2

HDU 5919 Sequence II 主席树

Sequence II Problem Description Mr. Frog has an integer sequence of length n, which can be denoted as a1,a2,?,an There are m queries. In the i-th query, you are given two integers li and ri. Consider the subsequence ali,ali+1,ali+2,?,ari. We can deno

hdu 5147 Sequence II(树状数组)

题目链接:hdu 5147 Sequence II 预处理每个位置作为b和c可以组成的对数,然后枚举b的位置计算. #include <cstdio> #include <cstring> #include <algorithm> using namespace std; typedef long long ll; const int maxn = 50005; int N, arr[maxn], fenw[maxn], lef[maxn], rig[maxn]; #d

hdu 5147 Sequence II (树状数组 求逆序数)

题目链接 Sequence II Time Limit: 5000/2500 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 331    Accepted Submission(s): 151 Problem Description Long long ago, there is a sequence A with length n. All numbers in this se

[ACM] hdu 5147 Sequence II (树状数组,前缀和,后缀和)

Sequence II Problem Description Long long ago, there is a sequence A with length n. All numbers in this sequence is no smaller than 1 and no bigger than n, and all numbers are different in this sequence. Please calculate how many quad (a,b,c,d) satis

HDOJ 5147 Sequence II 树阵

树阵: 每个号码的前面维修比其数数少,和大量的这后一种数比他的数字 再枚举每一个位置组合一下 Sequence II Time Limit: 5000/2500 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 121    Accepted Submission(s): 58 Problem Description Long long ago, there is a sequen

HDOJ 5147 Sequence II 树状数组

树状数组: 维护每一个数前面比它小的数的个数,和这个数后面比他大的数的个数 再枚举每个位置组合一下 Sequence II Time Limit: 5000/2500 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 121    Accepted Submission(s): 58 Problem Description Long long ago, there is a seq

bestcoder#23 1002 Sequence II 树状数组+DP

Sequence II Time Limit: 5000/2500 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 652    Accepted Submission(s): 164 Problem Description Long long ago, there is a sequence A with length n. All numbers in this sequenc

LeetCode: Permutations II 题解

Given a collection of numbers that might contain duplicates, return all possible unique permutations. For example,[1,1,2] have the following unique permutations:[1,1,2], [1,2,1], and [2,1,1].题解:依旧使用的是DFS的思想. 首先需要遍历输入数组,获取一共有多少种不同的数字,每个数字有多少个. 最简单的方法,