【优化】单调队列与dp
笔者大概看了一下单调队列对于DP的优化,故撰此文,望有帮助。
(dp还是推式子难啊qwq)
题目大意:在n个数的序列中,选择数字,使得其连续不超过k个数,且和最大。
本题的方程相对好推:设dp[i][0/1]为到了第i个数,且第i个数不选/选的最大值。
则有转移:dp[i][0]=max(dp[i-1][0],dp[i-1][1])
dp[i][1]=max{dp[j][0]-sum[j]+sum[i]},i-k<=j<i
枚举j即可。
但是题目会这么让你水过吗?
发现会超时,优化不可避免。
仔细观察方程,考虑它的特殊性。
对于方程1,我们不便再多做什么。但是对于方程2,显然仍有优化余地。
我们将sum[i]提出来,得到:
dp[i][1]=max{dp[j][0]-sum[j]}+sum[i].
这个方程只与j有关,我们让max里面的最大就好了。
维护它,我们可以用堆,也可以用单调队列,线段树。
本文主要讲对于单调队列的优化。它可以保证O(n)的时间复杂度。
首先,我们明确一点,我们维护的队首元素最大。显然,队列中的数字要单调递减。
其次,我们要严格确保我们查询的区间,保证队列中没有没用的数字。
并且每次枚举到下一个数的时候,注意更新队列。
考虑何时更新更优:
首先,当这个数字不在需要的范围的时候,删除即可。
其次,对于新插入的数字,我们要从队尾插入,比较哪个值更优:
判断它们的“浪费情况”即可。
用q[]表示队列,s[]表示前缀和,则判断:
s[q[head]]-f[q[head]][0]>s[i]-f[i][0]&&head<=tail
如果符合的话,就把它删掉吧。因为队尾的元素所浪费的比新插入的值多,显然一定不如它优。
由此,我们已经保证了单调队列的稳定复杂度。
给出代码:
#include<cstdio>
#include<iostream>
using namespace std;
long long q[2000000],f[2000000][2];
long long n,k,s[2000000],a[2000000];
long long tail,head;
int main(){
scanf("%lld%lld",&n,&k);
for(int i=1;i<=n;++i){
scanf("%lld",&a[i]);
s[i]=s[i-1]+a[i];//sum
}
tail=head=1;//初始化
for(int i=1;i<=n;++i){
f[i][0]=max(f[i-1][0],f[i-1][1]);//对于不选i,只考虑前面两个即可
while(q[head]<i-k&&head<=tail)head++;//判断队头是否在所找区间内
f[i][1]=f[q[head]][0]-s[q[head]]+s[i];//取MAX转移
while(f[i][0]-s[i]>f[q[tail]][0]-s[q[tail]]&&head<=tail)tail--;
q[++tail]=i;//更新队尾,当队列有数且当前队尾若插入i不满足单调性时
//写成s[i]-f[i][0]<s[q[tail]]-f[q[tail]][0]也可以
//可以理解为选到i和队尾时,两者不选的奶牛的效率和相比较,显然浪费少的更优,不优的删除即可
}printf("%lld\n",max(f[n][0],f[n][1]));
return 0;
}
双倍经验:P2034
持续更新中。
【优化】单调队列与dp的更多相关文章
- 【题解】Cats Transport (斜率优化+单调队列)
[题解]Cats Transport (斜率优化+单调队列) # When Who Problem Lang Verdict Time Memory 55331572 Jun/09/2019 19:1 ...
- BZOJ_1999_[Noip2007]Core树网的核_单调队列+树形DP
BZOJ_1999_[Noip2007]Core树网的核_单调队列+树形DP Description 设T=(V, E, W) 是一个无圈且连通的无向图(也称为无根树),每条边带有正整数的权,我们称T ...
- 【刷题笔记】DP优化-单调队列优化
单调队列优化 眼界极窄的ZZ之前甚至不会单调队列--(好丢人啊) 单调队列优化的常见情景: 转移可以转化成只需要确定一个维度,而且这个维度的取值范围在某个区间里 修剪草坪 这个题学长讲的好像是另外一个 ...
- BZOJ.1010.[HNOI2008]玩具装箱toy(DP 斜率优化/单调队列 决策单调性)
题目链接 斜率优化 不说了 网上很多 这的比较详细->Click Here or Here //1700kb 60ms #include<cstdio> #include<cc ...
- 完美字符子串 单调队列预处理+DP线段树优化
题意:有一个长度为n的字符串,每一位只会是p或j.你需要取出一个子串S(注意不是子序列),使得该子串不管是从左往右还是从右往左取,都保证每时每刻已取出的p的个数不小于j的个数.如果你的子串是最长的,那 ...
- [bzoj1010](HNOI2008)玩具装箱toy(动态规划+斜率优化+单调队列)
Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有 的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1.. ...
- Luogu【P1725】琪露诺(单调队列,DP)
本文是笔者第二篇解题报告.从现在开始,会将练的一些题发到博客上并归类到"解题报告"标签中. 琪露诺是这样一道题 这道题可以用纯DP做,但是据说会超时.(为什么?看起来过河这题比它数 ...
- 单调队列与DP
算是一个总结吧! 先来一个模板: TYVJ 1305 最大子序和 题目描述 输入一个长度为n的整数序列,从中找出一段不超过M的连续子序列,使得整个序列的和最大. 例如 1,-3,5,1,-2,3 当m ...
- 单调队列+线性dp题Watching Fireworks is Fun (CF372C)
一.Watching Fireworks is Fun(紫题) 题目:一个城镇有n个区域,从左到右1编号为n,每个区域之间距离1个单位距离节日中有m个烟火要放,给定放的地点ai,时间ti当时你在x,那 ...
随机推荐
- mac 下配置连接Linux服务器方法,上传下载文件操作
1.先按照文档在本地生成SSHkey 2.mac输入 sudo -i 进入超级管理员#模式下,然后 创建用户 #useradd XXXadmin #passwd XXXadmin XXXadmin用户 ...
- 目标识别AI资料
朋友推荐的, 还有自己搜的. 入门可以看看. 网上资料应该不少, 一搜一大把, 简单记下地址. Review of Deep Learning Algorithms for Object Detect ...
- 遇到doxygen生成的chm文档目录如果有中文是乱码?
原因不在于doxygen,它没有问题,问题出在微软的HTML Help Workshop的hhc.exe不支持utf8.所以要解决这个问题,需要做两个额外的步骤: 1.将html/index.hhp中 ...
- 【阿里云训练营】python查漏补缺 1
文章来自:微信公众号[机器学习炼丹术]. 有问题疑惑,或者想交流交朋友的可以加个人微信:cyx645016617 参考目录: 目录 1 注释 2 is 与 == 3 运算优先级 4 查找所有属性和方法 ...
- Java线程本质
java当中的线程和操作系统的线程是什么关系? 关于操作系统的线程 linux操作系统的线程控制原语 int pthread create(pthread t *thread, const pthre ...
- 阿里云前端路线 | CSS快速掌握
1.1什么是CSS 翻译为“层叠样式表”或者“级联样式表”, 简称样式表. 1.2CSS的主要作用 它主要是用来给HTML网页来设置外观或者样式 外观或者样式:HTML网页中的文字的大小.颜色.字体, ...
- 添加到web.config文件里的用户自定义翻页控件
<pages> <controls> <add tagPrefix="ucl" tagName="Pager_Backstage" ...
- 工具-Typora常用语法()+自己总结
工具-Typora常用语法 Markdown(MD)作为目前互联网写作相当流行的一种文档撰写语言格式,深受互联网编辑者的喜爱,由此周边一些基于MD的编辑工具也随之油然而生. 作为一款免费的MD编辑器: ...
- burpsuite抓包乱码问题
网上百度说只需要Change Font选择中文字体即可,但是我这边试过还是乱码,按照网上一篇博客说抓包中按钮展示乱码的问题,在下面Character Sets选择Use a specific char ...
- 第 8 篇:内容支持 Markdown 语法,接口返回包含解析后的 HTML
作者:HelloGitHub-追梦人物 在 Django博客教程(第二版) 中,我们给博客内容增加了 Markdown 的支持,博客详情接口应该返回解析后的 HTML 内容. 来回顾一下 Post 模 ...