前言:

自从发现1D/1D动态规划这个新的技能块后,每次看到这类题目都能口嗨成功,然后队友催我赶紧学。再者发现有好多优化方法,所以慢慢学,每天学一点,加上还要做一些奇奇怪怪的题目保持状态,也就差不多了。

第0天(1D/1D动态规划)

什么是1D/1D动态规划?
1D/1D动态规划是指形如dpi=max{dpj+w(i,j)}dp_{i}=max\{ dp_{j}+w(i,j)\}dpi​=max{dpj​+w(i,j)}的动态规划,当然maxmaxmax也可以换成minminmin。
据说长这样的dpdpdp一般都可以优化到o(nlogn)o(nlogn)o(nlogn)。
优化的思路就是在jjj的范围中,快速找到一个最优的转移点。
学习思路大概就是学习这个转移方程的不同类型,然后对于每种类型学习它的优化方法
学习链接(多去走走,这样笔者偷完知识就不会愧疚了,博客里会加入自己的东西(也许))

第0.5天(前缀和优化)

有个前缀和优化,这个笔者默认会了,就不学了。不会的话请读者自行学习。

第1天(单调队列优化)

啊~新的力量!
今天是单调队列优化dp,当然,就当大家都会单调队列了。
实话说,学完感觉原来的dpdpdp式也有点不恰当,我们把dpjdp_{j}dpj​也看作是w(i,j)w(i,j)w(i,j)中jjj的一部分运算,那式子其实就是dpi=max{w(i,j)}dp_{i}=max\{ w(i,j)\}dpi​=max{w(i,j)}。
好了,进入今天的正题。
按照我们的学习思路,我们应该对于此类优化,有一个归纳的转移式子,那就有了。

转移方程

dpi=max{w(j)}dp_{i}=max\{ w(j)\}dpi​=max{w(j)}

说明

这个方程的意思就是dpdpdp的转移只和jjj有关。然后这个jjj呢,一般是一个区间范围,并且随着iii的变大,jjj的范围区间是整体右移的。这样可以保证它能在转移过程中,用单调队列找到最优点。

思路:

说明中提到jjj的范围区间整体右移,我们设转移dpi−1dp_{i-1}dpi−1​时jjj的范围区间是[li−1,ri−1][l_{i-1},r_{i-1}][li−1​,ri−1​],转移dpidp_{i}dpi​时jjj的范围区间是[li,ri][l_{i},r_{i}][li​,ri​]。那么我们rrr变大的时候,就把新的元素加入到单调队列右边(如果要加的话,在这之前还要把右边一些不要的元素拿走),然后答案在队列左边找到范围内的。当然,这都是单调队列的东西,就不细讲了。

实战例题

PTA-Little Bird

题意

nnn棵树,每棵树有一个高度did_{i}di​,小HHH在第111棵树上,要跳到第nnn棵树上。在第iii棵树上时,可以跳到第i,i+1,…,i+ki,i+1,…,i+ki,i+1,…,i+k棵树上。每跳一次,如果高度不小于原来的高度,疲劳值就会加111。现在问小HHH从第111棵树上跳到第nnn棵树上,最少的疲劳值是多少。
(1≤n≤k≤106)(1\leq n\leq k\leq 10^{6})(1≤n≤k≤106)

思路

我们设状态dpidp_{i}dpi​表示跳到第iii棵树上需要花费的最少疲劳值。
那么有转移方程dpi=min{dpj+[di>=dj]}dp_{i}=min\{dp_{j}+[d_{i}>=d_{j}]\}dpi​=min{dpj​+[di​>=dj​]},其中j∈[i−k,i−1]j\in [i-k,i-1]j∈[i−k,i−1]。

我们要学习这个思路。
首先我们观察j∈[i−k,i−1]j\in [i-k,i-1]j∈[i−k,i−1],我们发现区间随着iii变大整体右移,成立。
然后dpj+[di>dj]dp_{j}+[d_{i}>d_{j}]dpj​+[di​>dj​],它是一个关于iii和jjj的式子,呃好像不成立。
这时候只能发挥我们的聪明才智了,咳咳。
我们先发现dpidp_{i}dpi​单调不下降,且每次增加都是加111。所以对于两个dpjdp_{j}dpj​的值,我们肯定直接取小的那个,因为小的那个+1+1+1也不会超过大的。然后对于两个相同的dpjdp_{j}dpj​,我们一定优先取djd_{j}dj​大的那个,也就是要在范围内找使得(−dpj,dj)(-dp_{j},d_{j})(−dpj​,dj​)最大的jjj。这样就可以用单调队列优化了。

刚才演示翻车了,我决定用dpi=w(i,j),whereg(j)ismaxforjinrangedp_{i}=w(i,j),where\;g(j)\;is\;max\;for\;j\;in\;rangedpi​=w(i,j),whereg(j)ismaxforjinrange来作为新式子。

这样也许就可以泛化模型了。

代码

题目有点卡,开o2优化就过了。
写完下班。

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef pair<int,int> P;int q[1000005],fr,bk;
int d[1000005];
int dp[1000005];
int w(int i,int j)
{return dp[j]+(d[i]>=d[j]);
}
P g(int j)
{return P(-dp[j],d[j]);
}
int main()
{int n;scanf("%d",&n);for(int i=1;i<=n;i++)scanf("%d",&d[i]);int m;scanf("%d",&m);while(m--){fr=bk=0;int k;scanf("%d",&k);dp[1]=0;q[bk++]=1;for(int i=2;i<=n;i++){while(q[fr]<i-k)fr++;dp[i]=w(i,q[fr]);while(!(fr==bk)&&g(q[bk-1])<=g(i))bk--;q[bk++]=i;}printf("%d\n",dp[n]);}return 0;
}

第二天(分治优化)

(待续。。)
(upd:更新了标题后面不应该加冒号的bug)
昨天是关于jjj独立的转移,依据jjj的单调性用单调队列优化。
那么今天这个是不关于jjj独立,即和iii和jjj都有关的,刚学了一种分治优化,当然你得先会分治。

转移方程

dpi=max(w(i,j)),j∈[1,i−1]dp_{i}=max(w(i,j)),j \in [1,i-1]dpi​=max(w(i,j)),j∈[1,i−1]
又或者说dpi=w(i,j),whereg(i,j)ismaxforjinrangedp_{i}=w(i,j),where\;g(i,j)\;is\;max\;for\;j\;in\;rangedpi​=w(i,j),whereg(i,j)ismaxforjinrange
并且还需要它的转移,随着iii满足某种决策单调性。

说明

总之,我们需要找的最优转移点和i,ji,ji,j都有关。
然后,转移要随着iii满足决策单调性。举个例子,大致意思是,当iii 慢慢变大,最优决策点jjj也会慢慢变大。但这不意味着jjj大更优,有些jjj压根不会被作为最优决策点,只是哪些对每个iii作为最优决策点的jjj们是随着iii变大而变大的(不下降)。

思路

分治的大致做法是,我们先找中间的dpmiddp_{mid}dpmid​的转移点qmidqmidqmid。然后根据决策单调性,当i<midi<midi<mid时,转移点j∈[1,qmid]j\in[1,qmid]j∈[1,qmid];当i>midi>midi>mid时,转移点j∈[qmid,n]j\in[qmid,n]j∈[qmid,n]且j<ij<ij<i。
然后每次这样取中点求最优转移点,把区间割成两个一半。递归深度是logloglog级的,那我们找转移点就暴力遍历可能存在最优转移点的决策区间。总体复杂度o(nlogn)o(nlogn)o(nlogn)。

实战例题

Lightning Conductor

题意

给定一个长度为nnn的序列{an}\{a_{n}\}{an​},对于每个 i∈[1,n]i\in [1,n]i∈[1,n],求出一个最小的非负整数ppp,使得 ∀j∈[1,n]\forall j\in[1,n]∀j∈[1,n],都有 aj≤ai+p−∣i−j∣a_j\le a_i+p-\sqrt{|i-j|}aj​≤ai​+p−∣i−j∣​
1≤n≤5×105,0≤ai≤1091\leq n\leq 5\times 10^{5},0\leq a_{i}\leq 10^{9}1≤n≤5×105,0≤ai​≤109

思路

我们令dpidp_{i}dpi​表示第iii个答案。
首先,把绝对值处理掉,我们可以正向跑一遍dpdpdp,再逆向跑一遍,求个最大值。
那么正向的转移方程就是dpi=max{aj−ai+i−j},j∈[1,i−1]dp_{i}=max\{a_{j}-a_{i}+\sqrt{i-j}\},j\in [1,i-1]dpi​=max{aj​−ai​+i−j​},j∈[1,i−1]。
关于iii常量先提出来,变成dpi=max{aj+i−j}−ai,j∈[1,i−1]dp_{i}=max\{a_{j}+\sqrt{i-j}\}-a_{i},j\in [1,i-1]dpi​=max{aj​+i−j​}−ai​,j∈[1,i−1]。
那么现在变成了,我们所说的模范转移式dpi=max{w(i,j)}dp_{i}=max\{w(i,j)\}dpi​=max{w(i,j)},其中w(i,j)=ai+i−jw(i,j)=a_{i}+\sqrt{i-j}w(i,j)=ai​+i−j​。
然后,它要满足我们所说的决策单调性,即iii变大的时候,我们选取的最优决策点jjj也会慢慢变大。我们观察式子wj(i)=ai+i−jw_{j}(i)=a_{i}+\sqrt{i-j}wj​(i)=ai​+i−j​是一个关于iii的函数,有i−1i-1i−1个这样的函数,我们要对于每个iii
选取一个最佳的函数wjw_{j}wj​,使得函数值最高。
然后我们发现这些函数的增长速度都是慢慢变慢的,且wjw_{j}wj​比wj+1w_{j+1}wj+1​在iii相同时增长速度要慢。也就是一旦iii增长到某个时候wjw_{j}wj​被一个wkw_{k}wk​超过了,且k>jk>jk>j,那么wjw_{j}wj​将永无翻身之日。
总的来说,就是满足当iii变大,最优决策点只会不断变大(或者换个题变小)。
满足我们前面所说的性质,然后就可以分治搞了。

代码:
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;double a[500005];
ll dp1[500005],dp2[500005];
double w(int i,int j)
{return a[j]+sqrt(abs(i-j))-a[i];
}
void solve(int l,int r,int ql,int qr,ll *dp)
{if(l>r||ql>qr)return ;int mid=(l+r)/2;int qmid=ql;for(int i=ql;i<=qr&&i<mid;i++)if(w(mid,i)>w(mid,qmid))qmid=i;dp[mid]=ceil(w(mid,qmid));solve(l,mid-1,ql,qmid,dp);solve(mid+1,r,qmid,qr,dp);
}
int main()
{int n;scanf("%d",&n);for(int i=1;i<=n;i++)scanf("%lf",&a[i]);solve(1,n,1,n,dp1);reverse(a+1,a+n+1);solve(1,n,1,n,dp2);reverse(dp2+1,dp2+n+1);for(int i=1;i<=n;i++)printf("%lld\n",max(0ll,max(dp1[i],dp2[i])));return 0;
}

第N天

(待续。。)
拿金了,先断更了

1D/1D动态规划学习总结相关推荐

  1. [HNOI2008]玩具装箱(1D/1D动态规划)

    [HNOI2008]玩具装箱 题目描述 P 教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中. P ...

  2. html z-dext优先级顺序,$ext{1D/1D}$ 动态规划的三种优化

    神必博主的沙雕前言 参考文献: 概念明晰 所谓 (ext{1D/1D}) 动态规划, 指的是状态数和单状态决策数都是 (O(n)) 的动态规划方程, 暴力求解的时间复杂度为 (O(n^2)). 四边形 ...

  3. 自适应动态规划学习笔记(3)

    @TOC 自适应动态规划学习笔记(3) 第三天(图全是偷的) 图1 ADP的三个部分 Model Network  书接上回,图(1)中所示的Model Network就是对于系统公式(1)xk+1= ...

  4. 动态规划学习记录:题型/思路汇总

    #动态规划学习记录# 动态规划学习记录:题型/思路汇总 一维数组动态规划 1.爬楼梯 2.数硬币 3.最大子序和 4.区域和检索 - 数组不可变 5.整数拆分 6.打家劫舍 7.打家劫舍II 8.解码 ...

  5. 1D/1D动态规划的三种优化方法

    1D/1D1D/1D1D/1D动态规划 形如dp[i]=min{dp[j]+w(j,i)}(Li≤j≤Ri)dp[i]=min\{dp[j]+w(j,i)\} (L_i\leq j\leq R_i)d ...

  6. 动态规划学习之三种方法解决斐波拉契数

    斐波拉契数是一个很经典的问题,也会很多公司面试的考题,每个学习计算机的同学都会接触这个问题,尤其是在学习递归的时候,利用递归来解决斐波拉契数是很多教材采用的一个例子,所以很多同学一想到斐波拉契马上就会 ...

  7. 动态规划学习的一波记录

    动态规划的概念 动态规划算法把原问题视作若干个重叠子问题的逐层递进,每个子问题的求解过程都构成了一个"阶段".在完成前一个阶段的计算后,动态规划才会执行下一个阶段的计算. 为了保证 ...

  8. 动态规划学习心得分享

    最近在代码随想录(代码随想录)刷了一些有关动态规划的算法题,收获还蛮大的,下面是我的一些学习心得分享,不足之处敬请批评指正~ 首先来简单介绍一下什么是动态规划以及动规与贪心有何区别? 动态规划(Dyn ...

  9. 算法-动态规划学习(含经典例子分析)

    文章目录 前言 一.动态规划是什么? 二.经典例子 爬楼梯问题 挖金矿问题 三.总结 前言 在leetcode刷题的过程中,碰到了许多动态规划相关的题目,故系统性的学习了动态规划算法.此文章总结了学习 ...

最新文章

  1. 各个数据库取前10行记录
  2. 其他算法-卡尔曼滤波器
  3. javascript: new Date(string)在IE中显示NaN的问题!
  4. Reporting Services 安装的备份和还原操作
  5. 解决cell循环利用造成的重复勾选
  6. CF1080F Katya and Segments Sets
  7. notempty注解属于哪个依赖_Spring框架 之@Valid注解的使用(嵌套类型的效验)
  8. local variable 'xxx' referenced before assignment
  9. Django模板层:模板继承 extends标签和block标签,csrf_token标签
  10. mysql数据库表无法显示_【MySQL8.0.18】IDEA 连接数据库无法显示数据表
  11. Linux分区和加密分区操作
  12. [Android] SharedPreferences(轻量级的存储方式)
  13. deepin显卡驱动管理器在哪_deepin显卡设置
  14. 2017吉比特校招一个编程笔试题
  15. python readcsv读取gbk编码文件_python读写csv文件
  16. 背景建模方法论文总结
  17. 基于深度学习的RGBD深度图补全算法文章鉴赏
  18. 奈学教育大数据架构分享下载
  19. Docker 从入门到入坑。
  20. 杰卡德相似系数(Jaccardsimilarity coefficient)

热门文章

  1. DNSPod十问Matt Overman:二维码真的代替域名了吗?
  2. 肥牛是不是牛肉,为什么?
  3. 将windows下文件编码格式转换成UTF-8 文件编码格式
  4. python为什么是蛇_【大蟒蛇】简谈Python的闭包【原创】
  5. php artisan migrate,laravel php artisan migrate错误
  6. java运行环境下载(我的世界Java运行环境)
  7. 中国成为北极理事会正式观察员国 将享合法权利
  8. 《MySQL必知必会》学习笔记——组合查询、全文本搜索
  9. 计算机设备的快捷命令,快速打开设备管理器的快捷键教程
  10. 《花千骨》为何被批“脑残”还能创造收视神话?