码迷,mamicode.com
首页 > 其他好文 > 详细

P3567 [POI2014]KUR-Couriers

时间:2019-11-11 11:14:11      阅读:67      评论:0      收藏:0      [点我收藏+]

标签:namespace   i++   pre   str   name   题目   cin   ace   int   

P3567 [POI2014]KUR-Couriers

题目:

题解:

  • 主席树节点开个sum记录l-r这几个数字出现的次数。
  • 查询的时候如果一段数的出现次数之和>区间长度/2,就往这一段数递归下去。当叶子节点满足>区间长度/2时,说明有数字出现次数超过了一半。
#include <iostream>
#include <cstdio>
#include <algorithm>
#define N 500005
#define find(x) (lower_bound(b + 1, b + 1 + cnt, x) - b)
using namespace std;

struct T {int l, r, sum;} t[N << 5];
int n, m, cnt, dex;
int a[N], b[N], rt[N];

int read()
{
    int x = 0, f = 1; char c = getchar();
    while(c < '0' || c > '9') {if(c == '-') f = -1; c = getchar();}
    while(c >= '0' && c <= '9') {x = x * 10 + c - '0'; c = getchar();}
    return x *= f;
}

int build(int l, int r)
{
    int p = ++dex, mid = l + r >> 1;
    if(l == r) return p;
    t[p].l = build(l, mid), t[p].r = build(mid + 1, r);
    return p;
}

int upd(int las, int l, int r, int val)
{
    int p = ++dex, mid = l + r >> 1;
    t[p].l = t[las].l, t[p].r = t[las].r, t[p].sum = t[las].sum + 1;
    if(l == r) return p;
    if(val <= mid) t[p].l = upd(t[las].l, l, mid, val);
    else t[p].r = upd(t[las].r, mid + 1, r, val);
    return p;
}

int ask(int u, int v, int l, int r, int val)
{
    int mid = l + r >> 1, res = 0;
    if(l == r) return l;
    if(t[t[v].l].sum - t[t[u].l].sum >= val) return ask(t[u].l, t[v].l, l, mid, val);
    if(t[t[v].r].sum - t[t[u].r].sum >= val) return ask(t[u].r, t[v].r, mid + 1, r, val);
    return 0;
}

int main()
{
    cin >> n >> m;
    for(int i = 1; i <= n; i++)
        a[i] = read(), b[++cnt] = a[i];
    sort(b + 1, b + 1 + n);
    cnt = unique(b + 1, b + 1 + cnt) - b - 1;
    rt[0] = build(1, cnt);
    for(int i = 1; i <= n; i++)
        rt[i] = upd(rt[i - 1], 1, cnt, find(a[i]));
    for(int i = 1; i <= m; i++)
    {
        int l = read(), r = read();
        int id = ask(rt[l - 1], rt[r], 1, cnt, (r - l + 1) / 2 + 1);
        printf("%d\n", b[id]);
    }
    return 0;
}

P3567 [POI2014]KUR-Couriers

标签:namespace   i++   pre   str   name   题目   cin   ace   int   

原文地址:https://www.cnblogs.com/BigYellowDog/p/11833626.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!