Description

我有一个元素个数为\(n\)的整数数组\(a\)和\(Q\)个问题,每个问题有\(x,y\)两个参数,我要数有多少个整数\(K\)满足\(K\)在\(a[x]…a[y]\)中出现了恰好\(K\)次。

题面就这么简单了。

Input

第一行两个整数\(n,Q\),表示数组\(a\)的元素个数和询问数;

接下来一行n给整数,描述数组a;

接下来Q行,每行两个数xi,yi(1<=xi<=yi<=n),表示询问的左右边界;

Output

输出Q行,每行一个整数表示满足询问的K的个数。

Sample Input

7 2

3 1 2 2 3 3 7

1 7

3 4

Sample Output

3

1

Hint

对于30%的数据,\(1 \le n,Q \le 1000\);

对于100%的数据,\(1 \le n,Q \le 100000,1 \le a[i] \le 10^9\);

sb莫队题目。。。1个元素支持\(O(1)\)加入。

#include<cmath>
#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstdlib>
using namespace std; #define maxn (100010)
int N,tot,Q,A[maxn],num[maxn],ans[maxn],lim,size; inline int gi()
{
char ch; int f = 1,ret = 0;
do ch = getchar(); while (!(ch >= '0'&&ch <= '9')&&ch != '-');
if (ch == '-') f = -1,ch = getchar();
do ret = ret*10+ch-'0',ch = getchar(); while (ch >= '0'&&ch <= '9');
return ret*f;
} struct node
{
int l,r,id;
inline void read(int i) { l = gi(),r = gi(); id = i; lim = max(lim,r); }
}query[maxn];
inline bool cmp1(const node &a,const node &b) { return a.l < b.l; }
inline bool cmp2(const node &a,const node &b) { return a.r < b.r; } inline void work()
{
int res = 0,L = query[1].l,R = query[1].r;
for (int i = L;i <= R;++i)
if (A[i] <= N)
{
if (num[A[i]] == A[i]) --res;
if (++num[A[i]] == A[i]) ++res;
}
for (int i = 1;i <= Q;++i)
{
while (R < query[i].r)
{
++R;
if (A[R] <= N)
{
if (num[A[R]] == A[R]) --res;
if (++num[A[R]] == A[R]) ++res;
}
}
while (R > query[i].r)
{
if (A[R] <= N)
{
if (num[A[R]] == A[R]) --res;
if (--num[A[R]] == A[R]) ++res;
}
--R;
}
while (L > query[i].l)
{
--L;
if (A[L] <= N)
{
if (num[A[L]] == A[L]) --res;
if (++num[A[L]] == A[L]) ++res;
}
}
while (L < query[i].l)
{
if (A[L] <= N)
{
if (num[A[L]] == A[L]) --res;
if (--num[A[L]] == A[L]) ++res;
}
++L;
}
ans[query[i].id] = res;
}
} int main()
{
freopen("1364.in","r",stdin);
freopen("1364.out","w",stdout);
N = gi(); Q = gi();
for (int i = 1;i <= N;++i) A[i] = gi();
for (int i = 1;i <= Q;++i) query[i].read(i);
size = ceil(sqrt(lim)+0.5);
sort(query+1,query+Q+1,cmp1);
for (int i = 1,j;i <= Q;i = j+1)
{
for (j = i;j < Q&&query[j+1].l - query[i].l <= size;++j);
sort(query+i,query+j+1,cmp2);
}
work();
for (int i = 1;i <= Q;++i) printf("%d\n",ans[i]);
fclose(stdin); fclose(stdout);
return 0;
}

sjtu1364 countcountcount的更多相关文章

随机推荐

  1. [转].net连oracle的问题及方法折腾总结 连接字串

    本文转自:http://www.th7.cn/Program/net/201305/138265.shtml 对oracle不算熟,对.net结合oracle开发项目也只做过一个.最近换了新电脑,装了 ...

  2. js数组求和

    array1.reduce(callbackfn[, initialValue]) callback : 函数执行在数组中每个值 initialValue : 对象作为第一个参数回调的第一次调用使用 ...

  3. (转)css3前缀

    CSS3的前缀是一个浏览器生产商经常使用的一种方式.它暗示该CSS属性或规则尚未成为W3C标准的一部分.看看都有哪些前缀: -webkit(chrome) -moz(firefox) -ms(ie) ...

  4. 如何让Div层悬浮在Flash Object对象之上(转载)

    今天有个用户,门户右上角的倒三角登陆小按钮在他的电脑上无法显示,他用的笔记本屏幕较小,宽度正好显示出页面内容,经查看,门户页眉使用的为flash对象. 大家都知道,如果想让某个图片或者Div层悬浮在别 ...

  5. Android——按钮的事件监听

    关于Button按钮的四种事件监听方法总结 首先我们在activity_main.xml里面先定义一个Button空间 <RelativeLayout xmlns:android="h ...

  6. 让aspx页面也可以通过url路由进行访问

    参考文章:http://blog.csdn.net/zhanglong_longlong/article/details/8841030 这两天,在工作中需要将aspx的页面虚拟成url路径访问.比如 ...

  7. MBR与分区表备份与恢复

    常用工具列表 dd                   数据复制,转换实用工具 tar                  GNU磁盘存档实用工具 cpio                数据存档实用工 ...

  8. (转)Quartz.NET管理类

    最近做项目设计到Quartz.NET,写了一个Quartz.NET管理类,在此记录下. public class QuartzManager<T> where T : class,IJob ...

  9. DB2数据库中提高INSERT性能详解

        分类: Linux INSERT 处理过程概述 首先让我们快速地看看插入一行时的处理步骤.这些步骤中的每一步都有优化的潜力,对此我们在后面会一一讨论. 在客户机准备 语句.对于动态 SQL,在 ...

  10. NFS vs. CIFS

    1.  CIFS协议分析 CIFS(Common Internet File System,公共互联网文件系统)是当前主流异构平台共享文件系统之一.主要应用在NT/Windows环境下,是由Micro ...