BZOJ 3585 mex 莫队算法+分块

题目大意:给定一个长度为n的数组,m次询问某个区间内的mex值

怒写莫队233

将权值分成√n块,记录每个权值的出现次数以及每块内有多少权值出现过

修改O(1)即可完成 查询时首先扫一遍找到第一个块内有没有覆盖的点的块 然后在块内暴力查找 时间复杂度O(√n)

套个莫队 总时间复杂度O(m√n)

#include <cmath>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#define M 200200
using namespace std;
struct abcd{
	int l,r,id;
	bool operator < (const abcd &x) const;
}queries[M];
int n,m,b;
int a[M],belong[M],l[M],r[M];
int L=1,R=0,f[M],block_ans[M],ans[M];
bool abcd :: operator < (const abcd &x) const
{
	if(belong[l]!=belong[x.l])
		return l<x.l;
	return r<x.r;
}
void Update(int x)
{
	if(x>n) return ;
	if(!f[x]++)
		block_ans[belong[x]]++;
}
void Downdate(int x)
{
	if(x>n) return ;
	if(!--f[x])
		block_ans[belong[x]]--;
}
int Query()
{
	int i;
	if(!f[0]) return 0;
	for(i=1;l[i];i++)
		if(block_ans[i]!=r[i]-l[i]+1)
			break;
	int temp=i;
	for(i=l[temp];i<=r[temp];i++)
		if(!f[i])
			return i;
	return n;
}
int main()
{
	int i;
	cin>>n>>m;
	b=int(sqrt(n)+1e-7);
	for(i=1;i<=n;i++)
		belong[i]=(i-1)/b+1;
	for(i=1;(i-1)*b+1<=n;i++)
		l[i]=(i-1)*b+1,r[i]=min(i*b,n);

	for(i=1;i<=n;i++)
		scanf("%d",&a[i]);
	for(i=1;i<=m;i++)
		scanf("%d%d",&queries[i].l,&queries[i].r),queries[i].id=i;
	sort(queries+1,queries+n+1);
	for(i=1;i<=m;i++)
	{
		while(R<queries[i].r)
			Update(a[++R]);
		while(L>queries[i].l)
			Update(a[--L]);
		while(R>queries[i].r)
			Downdate(a[R--]);
		while(L<queries[i].l)
			Downdate(a[L++]);
		ans[queries[i].id]=Query();
		L=queries[i].l;
		R=queries[i].r;
	}
	for(i=1;i<=m;i++)
		printf("%d\n",ans[i]);
	return 0;
}
时间: 2025-01-05 14:06:36

BZOJ 3585 mex 莫队算法+分块的相关文章

XOR and Favorite Number(莫队算法+分块)

E. XOR and Favorite Number time limit per test 4 seconds memory limit per test 256 megabytes input standard input output standard output Bob has a favorite number k and ai of length n. Now he asks you to answer m queries. Each query is given by a pai

【BZOJ】2038: [2009国家集训队]小Z的袜子(hose)(组合计数+概率+莫队算法+分块)

http://www.lydsy.com/JudgeOnline/problem.php?id=2038 学了下莫队,挺神的orz 首先如果推公式的话很简单吧.对于查询$[l,r]$ $$ans=\frac{\sum \binom{x_i}{2}}{\binom{r-l+1}{2}}$$ //晚修...回来补.. #include <cstdio> #include <cstring> #include <cmath> #include <string> #

莫队算法分块大小玄学调参指南

总算弄懂了这个分块大小怎么算... 两个指针 复杂度 \(O(u*n+\frac{n^2}{u})\) 根据均值不等式, \(u*n+\frac{n^2}{u}\) 在 \(u*n=\frac{n^2}{u}\) 时取最小值 即 \(u=\sqrt{n}\) 三个指针(带修) 复杂度 \(O(u*n+\frac{n^2}{u}+\frac{n^3}{u^2})\) 显然, \(\frac{n^2}{u}<\frac{n^3}{u^2}\) (作商法) 根据均值不等式, \(u*n+\frac{n

【BZOJ】3052: [wc2013]糖果公园 树分块+待修改莫队算法

[题目]#58. [WC2013]糖果公园 [题意]给定n个点的树,m种糖果,每个点有糖果ci.给定n个数wi和m个数vi,第i颗糖果第j次品尝的价值是v(i)*w(j).q次询问一条链上每个点价值的和或修改一个点的糖果ci.n,m,q<=10^5. [算法]树分块+带修改莫队算法 [题解]参考:WC 2013 糖果公园 park 题解 by vfleaking 首先树分块,参考王室联邦的方法.确定块大小为B,一遍DFS可以分成若干大小为[B,3B]的块,性质是块内两点距离至多为B. 定义(x,

[BZOJ 3236] [Ahoi2013] 作业 &amp;&amp; [BZOJ 3809] 【莫队 | 分块】

题目链接: BZOJ - 3236   BZOJ - 3809 算法一:莫队 首先,单纯的莫队算法是很好想的,就是用普通的第一关键字为 l 所在块,第二关键字为 r 的莫队. 这样每次端点移动添加或删除一个数字,用树状数组维护所求的信息就是很容易的.由于这里有 logn复杂度,所以复杂度还是挺高的. 于是 BZOJ-3236 的时限 100s,我的代码跑了 98s,险过...... However..BZOJ-3809 的出题人(SLYZ的神犇)就没有这么善良了!直接内存限制 28MB 就直接把

【莫队算法】【权值分块】bzoj3920 Yuuna的礼物

[算法一] 暴力. 可以通过第0.1号测试点. 预计得分:20分. [算法二] 经典问题:区间众数,数据范围也不是很大,因此我们可以: ①分块,离散化,预处理出: <1>前i块中x出现的次数(差分): <2>第i块到第j块中的众数是谁,出现了多少次. 询问的时候,对于整块的部分直接获得答案:对于零散的部分,暴力统计每个数出现 的次数,加上差分的结果,尝试更新ans. 时间复杂度O(m*sqrt(n)), 空间复杂度O(n*sqrt(n)). ②考虑离线,莫队算法,转移的时候使用数据

BZOJ 2038: [2009国家集训队]小Z的袜子(hose)【莫队算法裸题&amp;&amp;学习笔记】

2038: [2009国家集训队]小Z的袜子(hose) Time Limit: 20 Sec  Memory Limit: 259 MBSubmit: 9894  Solved: 4561[Submit][Status][Discuss] Description 作为一个生活散漫的人,小Z每天早上都要耗费很久从一堆五颜六色的袜子中找出一双来穿.终于有一天,小Z再也无法忍受这恼人的找袜子过程,于是他决定听天由命…… 具体来说,小Z把这N只袜子从1到N编号,然后从编号L到R(L 尽管小Z并不在意两

BZOJ 2038: [2009国家集训队]小Z的袜子(hose) [莫队算法]【学习笔记】

2038: [2009国家集训队]小Z的袜子(hose) Time Limit: 20 Sec  Memory Limit: 259 MBSubmit: 7687  Solved: 3516[Submit][Status][Discuss] Description 作为一个生活散漫的人,小Z每天早上都要耗费很久从一堆五颜六色的袜子中找出一双来穿.终于有一天,小Z再也无法忍受这恼人的找袜子过程,于是他决定听天由命……具体来说,小Z把这N只袜子从1到N编号,然后从编号L到R(L 尽管小Z并不在意两只

BZOJ 3236 AHOI 2013 作业 莫队算法

题目大意:给出一些数,问在一个区间中不同的数值有多少种,和在一个区间中不同的数值有多少个. 思路:由于没有修改,所以就想到了莫队算法.然后我写了5K+的曼哈顿距离最小生成树,然后果断T了.(100s的时限啊,刷status都要刷疯了..,结果最后加了手写读入也没能A).后来果断放弃,写了分块版的莫队算法.84sAC...这题卡的..貌似莫队并不是正解. 其实用分块来写莫队就很简单了.只需要将所有询问的区间排序,左端点所在块作为第一键值,右端点作为第二季键值排序,之后就可以转移了.理论上来时还是曼