BZOJ2724:[Violet 6]蒲公英
浅谈分块:https://www.cnblogs.com/AKMer/p/10369816.html
题目传送门:https://lydsy.com/JudgeOnline/problem.php?id=2724
对于每次询问的答案,要么是中间整块的众数,要么是在两侧不完整的块出现过的数。
根据这个性质,我们可以\(O(n\sqrt{n})\)求出每个块的众数和\(sum[i][j]\),表示从第一块到第\(i\)块内\(j\)出现了多少次。
然后再用区间\(dp\)在\(O(n\sqrt{n})\)的复杂度内求出\(mx[i][j]\),表示第\(i\)整块到第\(j\)整块的众数是多少。
对于每次询问,出现在两侧不完整的块的数,我们可以暴力扫描两侧把它们出现的次数丢到一个桶里,在加上在整块里出现的次数。
然后直接找次数最多的那个数就行了。
注意相同比大小要比原大小而不是离散化之后的大小。
时间复杂度:\(O(n\sqrt{n}+m\sqrt{n})\)
空间复杂度:\(O(n\sqrt{n})\)
代码如下:
#include <cmath>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
const int maxn=4e4+5;
int n,m,cnt,block,top,lstans;
int v[maxn],tmp[maxn],bel[maxn],tot[maxn];
int L[205],R[205],stk[405],mx[205][205],sum[205][maxn];
int read() {
int x=0,f=1;char ch=getchar();
for(;ch<'0'||ch>'9';ch=getchar())if(ch=='-')f=-1;
for(;ch>='0'&&ch<='9';ch=getchar())x=x*10+ch-'0';
return x*f;
}
int query(int l,int r,int v) {return sum[r][v]-sum[l-1][v];}
int main() {
n=read(),m=read(),block=sqrt(n);
for(int i=1;i<=n;i++) {
tmp[i]=v[i]=read();
bel[i]=(i-1)/block+1;
if(bel[i]!=bel[i-1])
R[bel[i-1]]=i-1,L[bel[i]]=i;
}
R[bel[n]]=n,sort(tmp+1,tmp+n+1);
cnt=unique(tmp+1,tmp+n+1)-tmp-1;
for(int i=1;i<=n;i++)
v[i]=lower_bound(tmp+1,tmp+cnt+1,v[i])-tmp;
for(int i=1;i<=bel[n];i++) {
memcpy(sum[i],sum[i-1],sizeof(sum[i]));
int num2=0;
for(int j=L[i];j<=R[i];j++)
sum[i][v[j]]++;
for(int j=L[i];j<=R[i];j++) {
int num1=query(i,i,v[j]);
if((num1>num2)||(num1==num2&&tmp[v[j]]<tmp[mx[i][i]]))
mx[i][i]=v[j],num2=num1;
}
}
for(int len=2;len<=bel[n];len++)
for(int i=1;i+len-1<=bel[n];i++) {
int j=i+len-1,res=mx[i][j-1],num2=query(i,j,res);
for(int k=L[j];k<=R[j];k++) {
int num1=query(i,j,v[k]);
if((num1>num2)||(num1==num2&&tmp[v[k]]<tmp[res]))
res=v[k],num2=num1;
}
mx[i][j]=res;
}
while(m--) {
int l=read(),r=read(),res=0,num2=0;
l=(l+lstans-1)%n+1,r=(r+lstans-1)%n+1;
if(r<l)swap(l,r);
if(bel[l]==bel[r]) {
for(int i=l;i<=r;i++)
if((++tot[v[i]])==1)stk[++top]=v[i];
}
else {
for(int i=l;i<=R[bel[l]];i++)
if((++tot[v[i]])==1) {
stk[++top]=v[i];
tot[v[i]]+=query(bel[l]+1,bel[r]-1,v[i]);
}
for(int i=L[bel[r]];i<=r;i++)
if((++tot[v[i]])==1) {
stk[++top]=v[i];
tot[v[i]]+=query(bel[l]+1,bel[r]-1,v[i]);
}
int tmp=mx[bel[l]+1][bel[r]-1];
if(!tot[tmp]) {
stk[++top]=tmp;
tot[tmp]=query(bel[l]+1,bel[r]-1,tmp);
}
}
for(int i=1;i<=top;i++) {
int num1=tot[stk[i]];
if((num1>num2)||(num1==num2&&tmp[stk[i]]<tmp[res]))
res=stk[i],num2=num1;
}
while(top)tot[stk[top--]]=0;
lstans=tmp[res];
printf("%d\n",lstans);
}
return 0;
}
BZOJ2724:[Violet 6]蒲公英的更多相关文章
- [BZOJ2724][Violet 6]蒲公英
[BZOJ2724][Violet 6]蒲公英 试题描述 输入 修正一下 l = (l_0 + x - 1) mod n + 1, r = (r_0 + x - 1) mod n + 1 输出 输入示 ...
- BZOJ2724 [Violet 6]蒲公英 分块
原文链接https://www.cnblogs.com/zhouzhendong/p/BZOJ2724.html 题目传送门 - BZOJ2724 题意 求区间最小众数,强制在线. $n$ 个数,$m ...
- bzoj2724: [Violet 6]蒲公英(离散化+分块)
我好弱啊..这题调了2天QwQ 题目大意:给定一个长度为n(n<=40000)的序列,m(m<=50000)次询问l~r之间出现次数最多的数.(区间众数) 这题如果用主席树就可以不用处理一 ...
- bzoj2724: [Violet 6]蒲公英 分块 区间众数 论algorithm与vector的正确打开方式
这个,要处理各个数的话得先离散,我用的桶. 我们先把每个块里的和每个块区间的众数找出来,那么在查询的时候,可能成为[l,r]区间的众数的数只有中间区间的众数和两边的数. 证明:若不是这里的数连区间的众 ...
- 【分块】bzoj2724 [Violet 6]蒲公英
分块,离散化,预处理出: ①前i块中x出现的次数(差分): ②第i块到第j块中的众数是谁,出现了多少次. 询问的时候,对于整块的部分直接获得答案:对于零散的部分,暴力统计每个数出现的次数,加上差分的结 ...
- bzoj2724: [Violet 6]蒲公英(分块)
传送门 md调了一个晚上最后发现竟然是空间开小了……明明算出来够的…… 讲真其实我以前不太瞧得起分块,觉得这种基于暴力的数据结构一点美感都没有.然而今天做了这道分块的题才发现分块的暴力之美(如果我空间 ...
- 【BZOJ2724】[Violet 6]蒲公英 分块+二分
[BZOJ2724][Violet 6]蒲公英 Description Input 修正一下 l = (l_0 + x - 1) mod n + 1, r = (r_0 + x - 1) mod n ...
- BZOJ 2724: [Violet 6]蒲公英
2724: [Violet 6]蒲公英 Time Limit: 40 Sec Memory Limit: 512 MBSubmit: 1633 Solved: 563[Submit][Status ...
- BZOJ 2724: [Violet 6]蒲公英( 分块 )
虽然AC了但是时间惨不忍睹...不科学....怎么会那么慢呢... 无修改的区间众数..分块, 预处理出Mode[i][j]表示第i块到第j块的众数, sum[i][j]表示前i块j出现次数(前缀和, ...
- BZOJ_2724_[Violet 6]蒲公英_分块
BZOJ_2724_[Violet 6]蒲公英_分块 Description Input 修正一下 l = (l_0 + x - 1) mod n + 1, r = (r_0 + x - 1) mod ...
随机推荐
- 教你在树莓派使用上RTC实时时钟,不用再担心断电后时间归零的问题,开机后自动同步RTC时钟!!!
准备工作:1.系统建议使用官方最新的镜像文件 2.RTC时钟模块板(I2C接口)建议使用DS1307时钟模块,或者RTC时钟模块RTC时钟模块: 大家知道arduino的电平是5V,树莓派是3.3V, ...
- 【Tech】CAS RESTful API使用笔记
在被maven,cas,tomcat各种贱人就是矫情的虐了好几天之后,终于跑通了demo,哈哈哈哈哈哈哈~ 在这里详细记录一下,给和我一样连maven都不会的小白一点福利,同时欢迎大神指正. 首先上最 ...
- 如何在java代码中调用一个web项目jsp或者servlet
有时候需要调用一个web项目的jsp或者servlet,但是执行内部的代码,并不是打开jsp,例如需要在一段java代码中清除一个web项目中的缓存,那么可以把清除缓存的代码放在该web项目的一个se ...
- 【转】Android BitmapShader 实战 实现圆形、圆角图片
转载自:http://blog.csdn.net/lmj623565791/article/details/41967509 1.概述 记得初学那会写过一篇博客Android 完美实现图片圆角和圆形( ...
- PAT1024. Palindromic Number (25)
输入即为回文的情况要考虑 #include <iostream> #include <algorithm> //reverse using namespace std; str ...
- jquery事件优化---事件委托
假如你有一个表格,里面有大量的td 而你需要做的事就是,给td绑定点击事件函数, 那么多的td,遍历单元格和为每一个单元格绑定事件处理函数将会大大降低代码的性能, 如果让单元格的父元素监听事件,只要判 ...
- STL视频_00
[05:40]比赛规则 - Part01[06:33]比赛规则 - Part02[07:28]比赛规则 - Part03[08:45]提出的问题 - 1和2[09:23]提出的问题 - 3和4 *** ...
- How to use the ZooKeeper driver for ServiceGroup in OpenStack Nova
ServiceGroup APIs Nova会从ServiceGroup API 中查询节点的存活信息. ServiceGroup API 工作流程是: 当一个compute worker (runn ...
- 搜索8--noi1817:城堡问题
搜索8--noi1817:城堡问题 一.心得 1.这题只是在普通的迷宫的基础上面加上了墙的概念,所以基本的思路和代码就和普通的迷宫是一样的,只不过需要多加上一层墙的判断 2.这里墙的判断是用的二进制加 ...
- TCP/IP 详解笔记
最早的 TCP 协议文档是 RFC793. TCP 提供一种面向连接的.可靠的字节流服务. 面向连接容易理解,那么什么是字节流服务呢? 答:两个应用程序通过 TCP 连接交换 8 bit 字节构成的字 ...