https://www.zybuluo.com/ysner/note/1298153

题面

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

  • \(n\leq10^5,m\leq2*10^5,a_i\leq n\)

    解析

    只出现过一次,就是上一次出现在位置\(l\)之前,下一次出现在位置\(r\)之后。
    这个有点像三维偏序,但这里有一维是区间啊。
    树套树续一下应该能过。

然而,对于维数较高的范围计数问题,\(kd-tree\)是更佳选择。
其复杂度稳定\(O(kn^{1-\frac{1}{k}})\)(\(k\)为维数),而且空间线性。

一般框架:

  • 如果当前节点存的点被询问范围包括,用这个点贡献答案
  • 如果当前节点的范围完全被询问范围包括,直接用整个节点贡献答案
  • 如果当前节点的范围(一个超立方体)和询问范围没有交,返回
  • 否则,递归进入左右儿子

对一个新加入的点,先自己更新自己的范围,再用儿子更新自己的范围。

把上一次,这一次,下一次这个数出现的位置看作三个维度就可以了。

#include<iostream>
#include<cmath>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#define ll long long
#define re register
#define il inline
#define ls t[k].l
#define rs t[k].r
#define fp(i,a,b) for(re int i=a;i<=b;i++)
#define fq(i,a,b) for(re int i=a;i>=b;i--)
using namespace std;
const int N=2e5+100;
int n,m,b[N],R[N],L[N],now,app[N],rt,ans;
il ll gi()
{re ll x=0,t=1;re char ch=getchar();while(ch!='-'&&(ch<'0'||ch>'9')) ch=getchar();if(ch=='-') t=-1,ch=getchar();while(ch>='0'&&ch<='9') x=x*10+ch-48,ch=getchar();return x*t;
}
il void cmin(re int &x,re int y){x=min(x,y);}
il void cmax(re int &x,re int y){x=max(x,y);}
struct dat
{int d[3],w,max;il bool operator < (const dat &o) const{return d[now]<o.d[now];}
}a[N];
struct node
{dat a;int l,r,mn[3],mx[3];
}t[N];
struct kd_tree
{il void upd(re int k,re int p){fp(i,0,2) cmin(t[k].mn[i],t[p].mn[i]),cmax(t[k].mx[i],t[p].mx[i]);t[k].a.max=max(t[k].a.max,t[p].a.max);}il void pushup(re int k){fp(i,0,2) t[k].mn[i]=t[k].mx[i]=t[k].a.d[i];if(ls) upd(k,ls);if(rs) upd(k,rs);}il void Build(re int &k,re int l,re int r,re int tag){re int mid=l+r>>1;now=tag;nth_element(a+l,a+mid,a+r+1);k=mid;t[k].a=a[mid];if(l<mid) Build(ls,l,mid-1,(tag+1)%3);else ls=0;if(mid<r) Build(rs,mid+1,r,(tag+2)%3);else rs=0;pushup(k);}il void Query(re int k,re int l,re int r){if(!k||t[k].a.max<ans) return;if(t[k].a.d[1]>=l&&t[k].a.d[1]<=r&&t[k].a.d[0]<l&&t[k].a.d[2]>r) ans=max(ans,t[k].a.w);if(t[k].mn[1]>=l&&t[k].mx[1]<=r&&t[k].mx[0]<l&&t[k].mn[2]>r) ans=max(ans,t[k].a.max);if(t[k].mn[1]>r||t[k].mx[1]<l||t[k].mn[0]>=l||t[k].mx[2]<=r) return;Query(ls,l,r);Query(rs,l,r);}
}kd;
int main()
{n=gi();m=gi();fp(i,1,n) b[i]=gi(),L[i]=app[b[i]],app[b[i]]=i,R[i]=n+1;fp(i,0,n) app[i]=n+1;fq(i,n,1) R[i]=app[b[i]],app[b[i]]=i;fp(i,1,n) a[i].d[0]=L[i],a[i].d[1]=i,a[i].d[2]=R[i],a[i].max=a[i].w=b[i];kd.Build(rt,1,n,0);while(m--){re int l=gi(),r=gi();l=(l+ans)%n+1,r=(r+ans)%n+1;if(l>r) swap(l,r);ans=0;kd.Query(rt,l,r);printf("%d\n",ans);}return 0;
}

转载于:https://www.cnblogs.com/yanshannan/p/9727305.html

[bzoj3489]A simple rmq problem相关推荐

  1. BZOJ3489 A simple rmq problem 【可持久化树套树】*

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

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

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

  3. BZOJ 3489: A simple rmq problem

    3489: A simple rmq problem Time Limit: 40 Sec  Memory Limit: 600 MB Submit: 1594  Solved: 520 [Submi ...

  4. [bzoj3489]A simple rmq problem_KD-Tree

    A simple rmq problem 题目大意:给定一个长度为$n$的序列,给出$m$个询问:在$[l,r]$之间找到一个在这个区间里只出现过一次的最大的数. 注释:$1\le n\le 10^5 ...

  5. 【BZOJ3489】A simple rmq problem(树套树)

    链接w:http://www.lydsy.com/JudgeOnline/problem.php?id=3489 题解:http://blog.csdn.net/PoPoQQQ/article/det ...

  6. bzoj 3489 A simple rmq problem——主席树套线段树

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3489 题解:http://www.itdaan.com/blog/2017/11/24/9b ...

  7. BZOJ 3489: A simple rmq problem(K-D Tree)

    Time Limit: 40 Sec  Memory Limit: 512 MB Submit: 2579  Solved: 888 [Submit][Status][Discuss] Descrip ...

  8. FZYZ-2071 A Simple Math Problem IX

    P2071 -- A Simple Math Problem IX 时间限制:1000MS      内存限制:262144KB 状态:Accepted      标签:    数学问题-博弈论    ...

  9. A Simple Math Problem(2020 ICPC 江西省省赛)

    A Simple Math Problem ∑i=1n∑j=1if(j)[gcd(i,j)=1]∑i=1n∑j=inf(i)[gcd(i,j)=1]∑i=1n∑j=1nf(i)[gcd(i,j)=1] ...

最新文章

  1. IOS使用Instrument-Time Profiler工具分析和优化性能问题
  2. 学java教程之this关键字
  3. C++大学教程(第九版)2016-07 保罗·戴特尔 (Paul Deitel)、 哈维·戴特尔 (Harvey Deitel)_cafbe(C++中文版)
  4. SVM(二)从拉格朗日对偶问题到SVM
  5. cmd java转jar包,cmd 打包java成jar可执行文件
  6. blufr 算法的理解---理解的不对的,欢迎拍砖
  7. 随想录(386cpu保护模式)
  8. windows平台下压缩tar.gz
  9. 服务器导流板的作用,前保险杠下导流板的作用是什么?
  10. Flink 如何读取和写入 Clickhouse?
  11. Camshift原理
  12. GDAL集成GEOS编译笔记
  13. 英文书信开头结尾模板
  14. 浅谈聊天机器人 ChatBot 涉及到的技术点 以及词性标注和关键字提取
  15. vue使用ruoyi框架自制icon图标
  16. 蓝牙耳机哪款好?2021无线蓝牙耳机测评
  17. 对菜鸟开发者的叮咛:花一万个小时练习 Coding,不要浪费一万小时无谓地 Debugging
  18. Android 仿今日头条、网易新闻的频道管理
  19. 微信公众号推广,选择哪一种类型文章产生共鸣
  20. Pycharm中,pyqt5.11.1的Qt assistant显示

热门文章

  1. 例子:倒计时按钮可用
  2. RecyclerView添加header与footer
  3. 常见浏览器兼容性问题与解决方案
  4. IOS多线程开发其实很简单
  5. [转]Open Data Protocol (OData) Basic Tutorial
  6. 项目总结(二)-一些常用的工具浅谈
  7. RDIFramework.NET ━ .NET快速信息化系统开发框架-4.3 平台主界面
  8. 记一次SQL Server2005导入Oracle10G的折腾过程【供多种数据库导入导出数据的C#程序源码参考】...
  9. 把虚拟系统接入网络 虚拟系统工作模式
  10. how to come in an investnent bank team