【BZOJ3489】A simple rmq problem

题面

bzoj

题解

这个题不强制在线的话随便做啊。。。

考虑强制在线时怎么搞

预处理出一个位置上一个出现的相同数的位置\(pre\)与下一个位置\(nxt\)

则对于一个询问\([l,r]\)

一个位置\(i\)当且仅当\(pre_i<l\)且\(nxt_i>r\)

我们可以将一个位置看作一个点坐标为\((pre_i,nxt_i)\)

要求横坐标\(<l\)且纵坐标\(>r\)

这个可以用简单\(kdTree\)

也可以用一个可持久化树套树强行维护一下

因为我写的时候还不会\(KDT\),所以用可持久化树套树强行维护了一波

#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <set>
using namespace std;
inline int gi() {
register int data = 0, w = 1;
register char ch = 0;
while (!isdigit(ch) && ch != '-') ch = getchar();
if (ch == '-') w = -1, ch = getchar();
while (isdigit(ch)) data = 10 * data + ch - '0', ch = getchar();
return w * data;
}
const int MAX_N = 100005;
int N, M;
struct Number { int val, pre, nxt, id; } a[MAX_N];
bool operator < (const Number &l, const Number r) { return l.pre < r.pre; }
struct Prestree { int ls, rs, rt; } t[MAX_N * 22];
struct SGT { int ls, rs, mx; } It[MAX_N * 18 * 18];
int rt[MAX_N], tot, cnt;
void ins(int &o, int p, int l, int r, int pos, int v) {
o = ++tot; It[o] = It[p], It[o].mx = max(It[o].mx, v);
if (l == r) return ;
int mid = (l + r) >> 1;
if (pos <= mid) ins(It[o].ls, It[p].ls, l, mid, pos, v);
else ins(It[o].rs, It[p].rs, mid + 1, r, pos, v);
}
void insert(int &o, int p, int l, int r, Number v) {
o = ++cnt; t[o] = t[p]; ins(t[o].rt, t[p].rt, 1, N, v.id, v.val);
if (l == r) return ;
int mid = (l + r) >> 1;
if (v.nxt <= mid) insert(t[o].ls, t[p].ls, l, mid, v);
else insert(t[o].rs, t[p].rs, mid + 1, r, v);
}
int que(int o, int l, int r, int ql, int qr) {
if (!o) return 0;
if (ql <= l && r <= qr) return It[o].mx;
int mid = (l + r) >> 1;
if (qr <= mid) return que(It[o].ls, l, mid, ql, qr);
else if (ql > mid) return que(It[o].rs, mid + 1, r, ql, qr);
else return max(que(It[o].ls, l, mid, ql, qr), que(It[o].rs, mid + 1, r, ql, qr));
}
int query(int o, int l, int r, int pl, int pr, int ql, int qr) {
if (!o) return 0;
if (pl <= l && r <= pr) return que(t[o].rt, 1, N, ql, qr);
int mid = (l + r) >> 1;
if (pr <= mid) return query(t[o].ls, l, mid, pl, pr, ql, qr);
else if (pl > mid) return query(t[o].rs, mid + 1, r, pl, pr, ql, qr);
else return max(query(t[o].ls, l, mid, pl, pr, ql, qr), query(t[o].rs, mid + 1, r, pl, pr, ql, qr));
}
set<int> s[MAX_N];
int ans = 0;
int main () {
N = gi(), M = gi();
for (int i = 1; i <= N; i++) s[i].insert(1), s[i].insert(N + 2);
for (int i = 1; i <= N; i++) a[i].val = gi(), s[a[i].val].insert(i + 1), a[i].id = i;
for (int i = 1; i <= N; i++) {
set<int> :: iterator ite = s[a[i].val].find(i + 1);
a[i].pre = *--ite, ++ite, a[i].nxt = *++ite;
}
sort(&a[1], &a[N + 1]);
for (int i = 1, j = 1; i <= N + 2; i++) {
rt[i] = rt[i - 1];
while (j <= N && a[j].pre == i) insert(rt[i], rt[i], 1, N + 2, a[j++]);
}
while (M--) {
int l = gi(), r = gi();
l = (l + ans) % N + 1;
r = (r + ans) % N + 1;
if (r < l) swap(l, r);
l++; r++;
printf("%d\n", ans = query(rt[l - 1], 1, N + 2, r + 1, N + 2, l - 1, r - 1));
}
return 0;
}

【BZOJ3489】A simple rmq problem的更多相关文章

  1. 【BZOJ3489】A simple rmq problem(KD-Tree)

    [BZOJ3489]A simple rmq problem(KD-Tree) 题面 BZOJ 题解 直接做肯定不好做,首先我们知道我们是一个二维平面数点,但是限制区间只能出现一次很不好办,那么我们给 ...

  2. 【BZOJ3489】A simple rmq problem kd-tree

    [BZOJ3489]A simple rmq problem Description 因为是OJ上的题,就简单点好了.给出一个长度为n的序列,给出M个询问:在[l,r]之间找到一个在这个区间里只出现过 ...

  3. 【bzoj3489】 A simple rmq problem

    http://www.lydsy.com/JudgeOnline/problem.php?id=3489 (题目链接) 题意 在线求区间不重复出现的最大的数. Solution KDtree竟然能够处 ...

  4. 【bzoj3489】 A simple rmq problem k-d树

    由于某些原因,我先打了一个错误的树套树,后来打起了$k-d$.接着因不明原因在思路上被卡了很久,在今天中午蹲坑时恍然大悟...... 对于一个数字$a_i$,我们可以用一组三维坐标$(i,pre,nx ...

  5. 【BZOJ3489】A simple rmq problem【kd树】

    题意 给出一个长度为n的序列,给出M个询问:在[l,r]之间找到一个在这个区间里只出现过一次的数,并且要求找的这个数尽可能大.如果找不到这样的数,则直接输出0.我会采取一些措施强制在线. 分析 预处理 ...

  6. 【bzoj3489】A simple rmq problem 三维KD-tree

    题目描述 因为是OJ上的题,就简单点好了.给出一个长度为n的序列,给出M个询问:在[l,r]之间找到一个在这个区间里只出现过一次的数,并且要求找的这个数尽可能大.如果找不到这样的数,则直接输出0.我会 ...

  7. 【BZOJ】【3489】A simple rmq problem

    KD-Tree(乱搞) Orz zyf教给蒟蒻做法 蒟蒻并不会这题正解……(可持久化树套树?...Orz 对于每个点,我们可以求出pre[i],nex[i],那么询问的答案就是:求max (a[i]) ...

  8. 【bzoj 3489】A simple rmq problem

    题目 \(kdt\)就是数点神器 我们先扫两遍处理出每个数上一次出现的位置\(pre_i,nxt_i\),之后变成\((i,pre_i,nxt_i)\)这样一个三维空间上的点 就变成了求一个立方体的最 ...

  9. BZOJ3489:A simple rmq problem

    浅谈\(K-D\) \(Tree\):https://www.cnblogs.com/AKMer/p/10387266.html 题目传送门:https://lydsy.com/JudgeOnline ...

随机推荐

  1. Java虚拟机9:垃圾收集(GC)-4(垃圾收集器)

    1.前言 垃圾收集器是前一章垃圾收集算法理论知识的具体实现了,不同虚拟机所提供的垃圾收集器可能会有很大差别,另外我们必须提前说明一个道理:没有最好的垃圾收集器,更加没有万能的收集器,只能选择对具体应用 ...

  2. python中的BaseManager通信(一)文件三分

    可以在windows下单机运行 主部分(提供服务器) #mainfirst.py from multiprocessing.managers import BaseManager import Que ...

  3. [19/04/16-星期二] 注解机制(Annotation,区别于comment(传统意义上的注释))

    一.概念 作用: ——不是程序本身,可以对程序作出解释.(这一点和注释没什么区别) ——可以被其它程序(比如编译器)读取,这是区别于注释的最重要的一点. 格式: ——"@注释名" ...

  4. Linux学习总结(十八)几个简单的文本处理工具cut sort tr split

    1 命令cut 用来截取某一个字段格式 : cut -d '分隔符' [-cf] n, n为数字,表示第几段-d:后面跟分隔符,分割符要加单引号-c:后面接的是第几个字符-f:后面接的是第几段那么意思 ...

  5. 8、Web Service-IDEA-jaxws规范下的 spring整合CXF

    前提:开发和之前eclipse的开发有很大的不同! 1.服务端的实现 1.新建项目 此时创建的是web项目 2.此时创建的项目是不完整的需要开发人员手动补充完整 3.对文件夹的设置(满满的软件使用方法 ...

  6. linq查询语法和方法-簡單用法

    來自:http://www.cnblogs.com/knowledgesea/p/3897665.html 1.简单的linq语法 //1 var ss = from r in db.Am_recPr ...

  7. Java实现发邮件功能

    代码如下: package com.weimob.finance.utils;import java.io.UnsupportedEncodingException;import java.util. ...

  8. Maven下使用Junit对Spring进行单元测试

    主要步骤 1. 在工程的pom文件中增加spring-test的依赖: <dependency> <groupId>org.springframework</groupI ...

  9. javascript中获取dom元素高度和宽度

    javascript中获取dom元素高度和宽度的方法如下: 网页可见区域宽: document.body.clientWidth网页可见区域高: document.body.clientHeight网 ...

  10. PAT——1060. 爱丁顿数

    英国天文学家爱丁顿很喜欢骑车.据说他为了炫耀自己的骑车功力,还定义了一个“爱丁顿数”E,即满足有E天骑车超过E英里的最大整数E.据说爱丁顿自己的E等于87. 现给定某人N天的骑车距离,请你算出对应的爱 ...