题目描述

输入

输出

样例输入

5 3

1 2 3 1 2

1 2

1 1

1 1

样例输出

4

数据范围

解法

考虑设置左指针l和右指针r;

维护[l,r]的关于等第的桶。

初始l=r=0;

每次右移r,加入新元素a[r];

如果桶因此爆了上限,则右移l并剔除a[l]直至桶不再爆上线。

(“桶爆上限”定义:某一元素的计数超过给定的区间的右端点)

每次右移结束后,如果所有元素的计数位于各自给定区间之内;

则就称这个[l,r]可以对答案进行贡献;


贡献的方式:

假定[l,r]区间内可以对答案进行贡献,

简单想一个O(n)的贡献方法,一直把l向右移直至[l,r]不再可以对答案贡献为止。

考虑优化,显然容易确定对于每种等第最多向右移多少位以保证区间可以进行贡献,设为x[i]。

那么贡献就等于所有x[i]的最小值。

在右移的时候顺便用线段树维护这个x。


题解给出了一种O(n)的方法。

代码

#include<iostream>
#include<stdio.h>
#include<math.h>
#include<string.h>
#include<algorithm>
#define ll long long
#define ln(x,y) ll(log(x)/log(y))
#define sqr(x) ((x)*(x))
using namespace std;
const char* fin="survey.in";
const char* fout="survey.out";
const ll inf=0x7fffffff;
const ll maxn=200007,maxt=maxn*4;/*注意!!!!!!!!*/
ll n,m,i,j,k,cnt,head,tmp;
ll ans;
ll a[maxn],tong[maxn],b[maxn][2];
ll c[maxt],fi[maxn],ta[maxn],ne[maxn],key[maxn];
bool bz=false;
void change(ll l,ll r,ll t,ll v,ll v1){
ll mid=(l+r)/2;
if (l==r) {
c[t]=v1;
return;
}
if (v<=mid) change(l,mid,t*2,v,v1);
else change(mid+1,r,t*2+1,v,v1);
c[t]=min(c[t*2],c[t*2+1]);
}
ll getmin(ll l,ll r,ll t,ll v1,ll v2){
ll mid=(l+r)/2;
if (l>v2 || r<v1) return inf;
if (l>=v1 && r<=v2) return c[t];
return min(getmin(l,mid,t*2,v1,v2),getmin(mid+1,r,t*2+1,v1,v2));
}
int main(){
freopen(fin,"r",stdin);
freopen(fout,"w",stdout);
scanf("%d%d",&n,&m);
memset(c,127,sizeof(c));
for (i=1;i<=n;i++) scanf("%d",&a[i]);
for (i=1;i<=m;i++) {
scanf("%d%d",&b[i][0],&b[i][1]);
if (b[i][0]==0) cnt++;
}
head=1;
for (i=1;i<=n;i++){
if (fi[a[i]]==0) fi[a[i]]=ta[a[i]]=i;
else ne[ta[a[i]]]=ta[a[i]]=i;
if (tong[a[i]]>=b[a[i]][0]){
tong[a[i]]++;
if (b[a[i]][0]==0) change(1,m,1,a[i],inf);
else {
key[a[i]]=ne[key[a[i]]],change(1,m,1,a[i],key[a[i]]);
}
while (tong[a[i]]>b[a[i]][1]){
bz=false;
if (tong[a[head]]>=b[a[head]][0]) bz=true;
tong[a[head]]--;
fi[a[head]]=ne[fi[a[head]]];
if (tong[a[head]]<b[a[head]][0] && bz) cnt--;
head++;
}
}else{
tong[a[i]]++;
if (tong[a[i]]==b[a[i]][0]){
cnt++;
key[a[i]]=fi[a[i]];
change(1,m,1,a[i],key[a[i]]);
}
}
if (cnt==m) {
ans+=getmin(1,m,1,1,m)-head+1;
}
}
printf("%lld",ans);
return 0;
}

启发

线性维护区间时,不妨考虑设置左右指针。

再联系数据结构来进行优化。

【JZOJ4804】【NOIP2016提高A组模拟9.28】成绩调研的更多相关文章

  1. 【JZOJ4803】【NOIP2016提高A组模拟9.28】求导

    题目描述 输入 输出 样例输入 2x^2+3x+1 样例输出 4x+3 数据范围 样例解释 求导的意思: 多项式是由若干个单项式构成的 单项式的一般形式是ax^b,其中ab都是常数,x是自变量 对于单 ...

  2. NOIP2016提高A组模拟9.28总结

    这次三道题都是可以AC的. 每道题思路都正确,但每道题都有细节没有注意. 第一题 1.没注意系数为1时可以省略系数: 2.没注意在第一项处理常数后,不能输出+号. 导致丢失20分:一定要多出特殊数据, ...

  3. 【JZOJ4805】【NOIP2016提高A组模拟9.28】跟踪

    题目描述 输入 输出 样例输入 4 2 1 3 1 2 2 3 3 4 样例输出 2 数据范围 解法 预处理出两个陌生人走到各个点的距离. 从石神处开始dfs,判断走到每一个点是否会被抓: 如果会,则 ...

  4. JZOJ 4732. 【NOIP2016提高A组模拟8.23】函数

    4732. [NOIP2016提高A组模拟8.23]函数 (Standard IO) Time Limits: 1500 ms  Memory Limits: 262144 KB  Detailed ...

  5. 【NOIP2016提高A组模拟9.14】数列编辑器

    题目 分析 比赛上,没有注意到询问只询问光标前面,于是只打了个暴力. 因为询问只询问光标前面,首先,当光标向后每移动到一个位置,顺便将这个位置的前缀和,和最大前缀和求出来. 总之,模拟 #includ ...

  6. 【NOIP2016提高A组模拟9.24】总结

    第一题纯模拟,结果那个出题人脑子似乎进水了,空间限制开了1G!!! 导致我捉摸了半天为什么空间要开那么大,最后只能得出上面的结论. 第二题是个矩阵快速幂,比赛上我没把递推式求出来,但是根据各种乱搞,得 ...

  7. 【JZOJ4746】【NOIP2016提高A组模拟9.3】树塔狂想曲

    题目描述 相信大家都在长训班学过树塔问题,题目很简单求最大化一个三角形数塔从上往下走的路径和.走的规则是:(i,j)号点只能走向(i+1,j)或者(i+1,j+1).如下图是一个数塔,映射到该数塔上行 ...

  8. 【JZOJ4745】【NOIP2016提高A组模拟9.3】看电影

    题目描述 听说NOIP2016大家都考得不错,于是CCF奖励省常中了 K 张变形金刚5的电影票奖励OI队的同学去看电影.可是省常中OI队的同学们共有 N(N >= K)人.于是机智的你想到了一个 ...

  9. 【JZOJ4787】【NOIP2016提高A组模拟9.17】数格子

    题目描述 输入 输出 样例输入 1 10000 3 10000 5 10000 0 0 样例输出 1 11 95 数据范围 每个测试点数据组数不超过10组 解法 状态压缩动态规划. 设f[i][j]表 ...

随机推荐

  1. typescript使用小结

    1. typescript使得js在书写的过程中有了参数类型的限制在 传参的过程中变得严格,减少了不必要的错误的发生 2. tslint同时也兼备了一部分eslint的作用,在一定程度上我们使用tsl ...

  2. MUI使用vue示例

    <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <meta name ...

  3. 进一步封装poco下的mysql操作

    为方便程序对mysql操作,我对poco的mysql进行了再次封装,主要是针对自己应用需要的部分. 开发工具:netbean 系统环境:centos7 poco版本: poco-1.9.0-all 主 ...

  4. python中的*args与**kwargs的含义与作用

    在定义函数的时候参数通常会使用 *args与**kwgs,形参与实参的区别不再赘述,我们来解释一下这两个的作用. *args是非关键字参数,用于元组,**kwargs是关键字参数 (字典)例如下面的代 ...

  5. 评价目标检测(object detection)模型的参数:IOU,AP,mAP

    首先我们为什么要使用这些呢? 举个简单的例子,假设我们图像里面只有1个目标,但是定位出来10个框,1个正确的,9个错误的,那么你要按(识别出来的正确的目标/总的正确目标)来算,正确率100%,但是其实 ...

  6. c++新特性实验(3)声明与定义:constexpr

    1.作用 constexpr 声明一个函数或变量,它的值可以在编译时出现在常量表达式之中. 2.constexpr 变量要求 其类型必须是 字面类型 (LiteralType) . 它必须被立即初始化 ...

  7. HTTP协议①介绍

    HTTP协议(HyperText Transfer Protocol,超文本传输协议)是因特网上应用最为广泛的一种网络传输协议,所有的WWW文件都必须遵守这个标准. HTTP是一个基于TCP/IP通信 ...

  8. 优雅的css写法

    一.利用好代码折叠 css也可以进行优雅的代码折叠而且会比html更好看 折叠后的效果: 这样就可以很舒服的把它折叠起来. 二.向Twitter Bootstrap学习 1. 学习的第一点就是用cla ...

  9. Constructing Roads POJ - 2421 (最小生成树)

    思路:首先使用二维数组dis[][]处理输入, 对于已经修好的路,将其对应的dis[i][j]置为零即可.最后再将    所有的dis[][]保存到边结构体中,使用Kruskal算法求得最小生成树. ...

  10. vue单页应用中,使用setInterval()定时向服务器获取数据,后来跳转页面后,发现还在不停的获取数据。

    使用VUE开发单页项目时遇到这样的问题,mounted中使用setInterval()定时向服务器获取数据,后来跳转页面后,发现还在不停的获取数据.我以为是因为我路由用的push导致的,改成repla ...