洛谷P1198 [JSOI2008]最大数(BZOJ.1012 )
题目描述
现在请求你维护一个数列,要求提供以下两种操作:
1、 查询操作。
语法:Q L
功能:查询当前数列中末尾L个数中的最大的数,并输出这个数的值。
限制:L不超过当前数列的长度。
2、 插入操作。
语法:A n
功能:将n加上t,其中t是最近一次查询操作的答案(如果还未执行过查询操作,则t=0),并将所得结果对一个固定的常数D取模,将所得答案插入到数列的末尾。
限制:n是整数(可能为负数)并且在长整范围内。
注意:初始时数列是空的,没有一个数。
输入输出格式
输入格式:
第一行两个整数,M和D,其中M表示操作的个数(M <= 200,000),D如上文中所述,满足(0<D<2,000,000,000)
接下来的M行,每行一个字符串,描述一个具体的操作。语法如上文所述。
输出格式:
对于每一个查询操作,你应该按照顺序依次输出结果,每个结果占一行。
输入输出样例
5 100
A 96
Q 1
A 97
Q 1
Q 2
96
93
96
说明
[JSOI2008]
思路:
1.线段树。在初始建树时将所有节点赋值为-INF,操作和单点修改与区间最值并没有多少不同。
2.单调队列+二分查找。
代码:
1.线段树 722ms/17.06MB,比方法2要慢近一倍。
#include<cstdio>
#include<algorithm>
#define LL long long
using namespace std;
const int N=,INF=1e9+; int m,mod,len;
LL t,Max[N<<]; void read(int &now)
{
now=;bool f=;char c=getchar();
while(c<''||c>'')
{
if(c=='-')f=;
c=getchar();
}
while(c>=''&&c<='')now=(now<<)+(now<<)+c-'',c=getchar();
now= f?-now:now;
} void PushUp(int rt)
{
Max[rt]= Max[rt<<]<Max[rt<<|]?Max[rt<<|]:Max[rt<<];
} void Build(int l,int r,int rt)
{
if(l==r)
{
Max[rt]=-INF;
return;
}
int m=(l+r)>>;
Build(l,m,rt<<);
Build(m+,r,rt<<|);
PushUp(rt);
} void ModifyPoint(int l,int r,int rt,int p,int v)
{
if(l==r)
{
Max[rt]= Max[rt]<v?v:Max[rt];
return;
}
int m=(l+r)>>;
if(p<=m) ModifyPoint(l,m,rt<<,p,v);
else ModifyPoint(m+,r,rt<<|,p,v);
PushUp(rt);
} LL QueryMax(int l,int r,int rt,int L,int R)
{
if(L<=l && r<=R) return Max[rt];
int m=(l+r)>>;
LL res=-INF;
if(L<=m) res=max(res,QueryMax(l,m,rt<<,L,R));
if(m<R) res=max(res,QueryMax(m+,r,rt<<|,L,R));
return res;
} int main()
{
read(m);read(mod);
Build(,m,);
for(int i=;i<=m;++i)
{
char opt[];int num;
scanf("%s",opt);read(num);
if(opt[]=='A')
ModifyPoint(,m,,++len,(num+t)%mod);
else
printf("%lld\n",t=QueryMax(,m,,len-num+,len));
}
return ;
}
线段树(插入元素 区间最值)
2.单调队列+lower_bound(+栈) 337ms/12.6MB
(先写 if(opt[0]=='Q')+询问 后写插入 就会错是什么鬼。。 哪位dalao看出来帮我指出一下。。thanks)
#include<cstdio>
#include<algorithm>
using namespace std;
const int N=; int m,mod,len,size,t,Num[N],Stack[N]; void read(int &now)
{
now=;bool f=;char c=getchar();
while(c<''||c>'')
{
if(c=='-')f=;
c=getchar();
}
while(c>=''&&c<='')now=(now<<)+(now<<)+c-'',c=getchar();
now= f?-now:now;
} /*int Mylower_bound(int s,int t,int p)
{
int l=s,r=t,m;
while(l<r)
{
m=(l+r)>>1;
if(Stack[m]<p)
l=m+1;
else if(Stack[m]==p)
return m;
else
r=m;
}
return l;
}*/ int main()
{
read(m);read(mod);
char opt[];int a;
while(m--)
{
scanf("%s",opt);read(a);
if(opt[]=='A')
{//因为比当前元素小的数在最后的求最大值中毫无作用,所以直接弹出
a=(a+t)%mod;
Num[++len]=a;
while(size && Num[Stack[size]]<=a)
--size;
Stack[++size]=len;
}
else
{//Stack[i]存储的是一个位置pos,且这些位置单调递增,这些位置对应的Num[pos]也单调递增
int pos=lower_bound(Stack+,Stack+size+,len-a+)-Stack;//找出一个Stack中大于等于查询位置的pos
//int pos=Mylower_bound(1,size,len-a+1);
printf("%d\n",t=Num[Stack[pos]]);
}
}
return ;
}
单调队列
错误的写法
#include<cstdio>
#include<algorithm>
using namespace std;
const int N=; int m,mod,len,size,t,Num[N],Stack[N]; void read(int &now)
{
now=;bool f=;char c=getchar();
while(c<''||c>'')
{
if(c=='-')f=;
c=getchar();
}
while(c>=''&&c<='')now=(now<<)+(now<<)+c-'',c=getchar();
now= f?-now:now;
} int main()
{
read(m);read(mod);
char opt[];int a;
while(m--)
{
scanf("%s",opt);read(a);
if(opt[]=='Q')
{//Stack[i]存储的是一个位置,且这些位置单调递增,这些位置对应的Num[pos]也单调递增
int pos=lower_bound(Stack+,Stack+size+,len-a+)-Stack;
printf("%d\n",t=Num[pos]);
}
else
{//因为比当前元素小的数在最后的求最大值中毫无作用,所以直接弹出
a=(a+t)%mod;
Num[++len]=a;
while(size && Num[Stack[size]]<=a)
--size;
Stack[++size]=len;
}
}
return ;
}
0分
洛谷P1198 [JSOI2008]最大数(BZOJ.1012 )的更多相关文章
- 洛谷 P1198 [JSOI2008]最大数
洛谷 P1198 [JSOI2008]最大数 题目描述 现在请求你维护一个数列,要求提供以下两种操作: 1. 查询操作. 语法:Q L 功能:查询当前数列中末尾L个数中的最大的数,并输出这个数的值. ...
- 洛谷P1198 [JSOI2008]最大数(单点修改,区间查询)
洛谷P1198 [JSOI2008]最大数 简单的线段树单点问题. 问题:读入A和Q时,按照读入一个字符会MLE,换成读入字符串就可以了. #include<bits/stdc++.h> ...
- 「线段树」「单点修改」洛谷P1198 [JSOI2008]最大数
「线段树」「单点修改」洛谷P1198 [JSOI2008]最大数 题面描述 现在请求你维护一个数列,要求提供以下两种操作: 1. 查询操作. 语法:Q L 功能:查询当前数列中末尾L个数中的最大的数, ...
- 洛谷P1198 [JSOI2008]最大数
P1198 [JSOI2008]最大数 267通过 1.2K提交 题目提供者该用户不存在 标签线段树各省省选 难度提高+/省选- 提交该题 讨论 题解 记录 最新讨论 WA80的戳这QwQ BZOJ都 ...
- 【题解】洛谷P1198 [JSOI2008] 最大数(线段树)
洛谷P1198:https://www.luogu.org/problemnew/show/P1198 思路 一道水水的线段树 20分钟A掉 这道题只涉及到单点修改和区间查询 所以这道题甚至不用Laz ...
- BZOJ——1012: [JSOI2008]最大数maxnumber || 洛谷—— P1198 [JSOI2008]最大数
http://www.lydsy.com/JudgeOnline/problem.php?id=1012|| https://www.luogu.org/problem/show?pid=1198 T ...
- 洛谷 P1198 [JSOI2008]最大数 Label:线段树
题目描述 现在请求你维护一个数列,要求提供以下两种操作: 1. 查询操作. 语法:Q L 功能:查询当前数列中末尾L个数中的最大的数,并输出这个数的值. 限制:L不超过当前数列的长度. 2. 插入操作 ...
- 洛谷 P1198 [JSOI2008]最大数——单调栈/线段树
先上一波题目 https://www.luogu.org/problem/P1198 题目要求维护后缀最大值 以及在数列的最后面添加一个数 这道题呢我们有两种做法 1.单调栈 因为只需要维护后缀最大值 ...
- 洛谷P1198 [JSOI2008]最大数(线段树/单调栈)
题目链接: https://www.luogu.org/problemnew/show/P1198 题目描述 现在请求你维护一个数列,要求提供以下两种操作: 1. 查询操作. 语法:Q L 功能:查询 ...
随机推荐
- Dubbo服务超时
服务消费者引用服务提供者的服务时可能由于网络原因导致长时间未返回相应,此时大量的线程将会阻塞,引起性能下降等问题.可以通过引入服务超时来解决该问题 服务超时指服务在给定的时间内未返回相应将立即终止该请 ...
- 【API】检查进程是否存在 - CreateToolhelp32Snapshot
1 学习目标 今天静态逆向mydocument病毒时,看到病毒代码为了防止自身被调试会先检测杀毒软件和调试工具的进程是否存在.如果没有杀毒软件则释放真正的病毒文件,提前熟悉一下枚举进程的反汇编代码. ...
- MR数据生成工具指向目录
mrDataTidy_SaveTwoDays.jar 原始路径 :D:\太原MR数据\一天数据整理 目标路径 : D:\MR现场数据整理\保存两天_整理后数据 例如 当前时间:2017-5-17 10 ...
- Linux: 介绍make menuconfig中的每个选项含义【转】
转自:http://blog.csdn.net/gaoyuanlinkconcept/article/details/8810468 介绍make menuconfig中的每个选项含义 Linux 2 ...
- Json对象和字符串互相转换 数据拼接 JSON使用方式
JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式. 一.JSON字符串转换为JSON对象: eval() 和 JSON.parse eg- json字符串: ...
- 003_Linux的Cgroup<实例详解>
为什么要有cgroup Linux系统中经常有个需求就是希望能限制某个或者某些进程的分配资源.也就是能完成一组容器的概念,在这个容器中,有分配好的特定比例的cpu时间,IO时间,可用内存大小等.于是就 ...
- CentOS 6.5自动化运维之基于DHCP和TFTP服务的PXE自动化安装centos操作系统详解
前言 如果要给很多台客户端主机安装操作系统,要是每一台都拿张安装光盘一台一台主机的去装系统那就太浪费时间和精力了.在生产环境中也不实际,要实现为多台主机自动安装操作系统,那我们怎么实现自动化安装 ...
- 转载:2.2.4 配置项的单位《深入理解Nginx》(陶辉)
原文:https://book.2cto.com/201304/19629.html 大部分模块遵循一些通用的规定,如指定空间大小时不用每次都定义到字节.指定时间时不用精确到毫秒. 当指定空间大小时, ...
- Android OAuth认证
OAuth认证 为了安全地访问在线服务,用户需要在服务上进行身份验证,即要提供他们的身份的证明.对于一个要访问第三方服务的程序来说,安全问题甚至更复杂.不仅仅是用户需要在访问服务前要进行身份验证,而且 ...
- citySelect省市区jQuery联动插件
参考地址:http://blog.csdn.net/qq_33556185/article/details/50704446 参考地址:http://www.lanrenzhijia.com/jque ...