BZOJ4241 历史研究(莫队)
如果分块的话与区间众数没有本质区别。这里考虑莫队。
显然莫队时的删除可以用堆维护,但多了一个log不太跑得过。
有一种叫回滚莫队的trick,可以将问题变为只有加入操作。按莫队时分的块依次处理,一块中左端点的差不超过√n,右端点单调递增。首先将右端点也在该块中的询问暴力处理。然后令指针l在下一块开头,指针r在这一块结尾。暴力扩展右端点移动指针r,到达询问点时,移动指针l以回答询问,但不让指针l的移动对之后的询问产生影响,即回滚。这样就可以处理删除了。
#include<iostream> #include<cstdio> #include<cmath> #include<cstdlib> #include<cstring> #include<algorithm> using namespace std; 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<<1)+(x<<3)+(c^48),c=getchar();return x*f; } #define N 100010 #define ll long long int n,m,a[N],b[N],cnt[N]; ll ans[N]; struct data {int x,y,k,i;bool operator <(const data&a) const{return k<a.k||k==a.k&&y<a.y;} }q[N]; int main() { #ifndef ONLINE_JUDGEfreopen("bzoj4241.in","r",stdin);freopen("bzoj4241.out","w",stdout);const char LL[]="%I64d\n"; #elseconst char LL[]="%lld\n"; #endifn=read(),m=read();for (int i=1;i<=n;i++) b[i]=a[i]=read();sort(b+1,b+n+1);int t=unique(b+1,b+n+1)-b-1;for (int i=1;i<=n;i++) a[i]=lower_bound(b+1,b+t+1,a[i])-b;int block=sqrt(n);for (int i=1;i<=m;i++) q[i].x=read(),q[i].y=read(),q[i].k=q[i].x/block,q[i].i=i;sort(q+1,q+m+1);for (int i=1;i<=m;i++){int t=i;while (t<m&&q[t+1].k==q[i].k) t++;while (i<=t&&q[i].y<(q[i].k+1)*block){for (int j=q[i].x;j<=q[i].y;j++){cnt[a[j]]++;ans[q[i].i]=max(ans[q[i].i],1ll*cnt[a[j]]*b[a[j]]);}for (int j=q[i].x;j<=q[i].y;j++) cnt[a[j]]--;i++;}int r=(q[i].k+1)*block-1;ll v=0;for (int j=i;j<=t;j++){while (r<q[j].y){cnt[a[++r]]++;v=max(v,1ll*cnt[a[r]]*b[a[r]]);}ans[q[j].i]=v;for (int k=(q[i].k+1)*block-1;k>=q[j].x;k--){cnt[a[k]]++;ans[q[j].i]=max(ans[q[j].i],1ll*cnt[a[k]]*b[a[k]]);}for (int k=(q[i].k+1)*block-1;k>=q[j].x;k--) cnt[a[k]]--;}memset(cnt,0,sizeof(cnt));i=t;}for (int i=1;i<=m;i++) printf(LL,ans[i]);return 0; }
转载于:https://www.cnblogs.com/Gloid/p/9833040.html
BZOJ4241 历史研究(莫队)相关推荐
- BZOJ4241历史研究题解--回滚莫队
题目链接 https://www.lydsy.com/JudgeOnline/problem.php?id=4241 分析 这题就是求区间权值乘以权值出现次数的最大值,一看莫队法块可搞,但仔细想想,莫 ...
- 【练习】BZOJ4241: 历史研究(回滚莫队)
题意 给定一个长度为 n n n的序列,并提出q" role="presentation">qqq个询问,每次询问要求回答区间 [l,r] [ l , r ] [l ...
- 【周末狂欢赛6】[AT1219]历史研究(回滚莫队),大魔法师(矩阵+线段树),单峰排列
文章目录 T1:单峰排列 题目 题解 code T2:历史研究 题目 题解 code T3:大魔法师 题目 题解 code 我可能这辈子都更不出来狂欢赛5了,先咕咕 T1:单峰排列 题目 一个n的全排 ...
- 历史研究(回滚莫队)
问题 C: 历史研究 时间限制: 1 Sec 内存限制: 128 MB 提交: 61 解决: 2 [提交] [状态] [命题人:admin] 题目描述 IOI 国历史研究的大牛--JOI 教授,最 ...
- AT1219-歴史の研究(历史研究)【回滚莫队】
正题 题目链接:https://www.luogu.com.cn/problem/AT1219 题目大意 nnn个数字,mmm次询问一个区间内ti∗it_i*iti∗i的最大值,tit_iti即区 ...
- BZOJ 4241: 历史研究
Description IOI国历史研究的第一人--JOI教授,最近获得了一份被认为是古代IOI国的住民写下的日记.JOI教授为了通过这份日记来研究古代IOI国的生活,开始着手调查日记中记载的事件. ...
- 【HNOI2016】序列【莫队】【单调栈】【ST表】
题意:给定序列 aia_iai,qqq 次询问 [l,r][l,r][l,r] 所有子区间最小值之和. n,q≤105n,q\leq 10^5n,q≤105 这种题一眼看上去是离线线段树,但这题每移 ...
- [HNOI2016] 序列(线段树 + 莫队 + 倍增)
problem luogu-P3246 心路历程+卡常历程+问题存疑 一直在想莫队的做法.发现左右指针的移动对应一段左/右端点固定的子序列,然后可以一个数代表一段相同的贡献. 就开始求 lsti,nx ...
- 莫队算法(普通莫队、带修莫队、树上莫队、不删除莫队)学习笔记【理解+套路/核心代码+例题及题解】
一.理解 我的理解就是巧妙的暴力,利用双指针以及分块思想,巧妙的移动双指针,时间复杂度可以达到O(NlogN). 强推博客:写的又好又全.链接 二.套路 1.普通莫队 [1]核心代码 bool cmp ...
最新文章
- 2010中国城市GDP排名
- python怎么读excel文件-python 读取excel文件
- python如何统计字典里面健的数量_Python中使用Counter进行字典创建以及key数量统计的方法...
- iso linux 内核版本号_Linux查看 iso 版本信息
- Linux下,使用nginx+ffmpeg+video.js实现直播效果(含centos7环境配置步骤)
- CreateService / SC 创建自启动服务
- 产线数字化软件源码_数字化工厂规划的十大核心要素
- pringMVC“Ambiguous mapping found. Cannot map 'XXXController' bean method”解决方法
- $* $@ $# $? $$ $! $0 $_
- 用计算机唱出惊雷,除了《惊雷》还有多少喊麦神曲?这十首神作你一定听过!...
- ERROR! The server quit without updating PID file (/usr/local/var/mysql/apple,卸载,重装一个,我的方案
- 前端名称命名--英文字母
- 惠普招聘 运维质量管理顾问 1名 北京
- vsn服务器 需要先建项目才能,急求!项目马上上线,但是Oracle服务器存在问题...
- 机器学习基石笔记2——在何时可以使用机器学习(2)
- 待熟悉的工具或API清单列表
- mui ajax的值php怎样获取,MUI.ajax是怎么获取数据的
- Mysql中key 、primary key
- chrome浏览器上传文件fakepath问题
- 北航计算机考研录取多少人,北航计算机考研近三年报考录取情况