(长期更新)DP 优化 学习笔记

  • 空间优化
  • 时间优化

  • 状态方面的优化
  • 转移方面的优化
    • 快速寻找决策点
    • 批量转移
      • 从一批状态转移来
      • 转移到一批状态

纯粹的空间优化

滚动数组 & 类似滚动数组的

本质:某个时刻,某些状态现在和以后都不会再被用到了,于是让新的状态覆盖掉这些状态。

滚动数组常用取模(特殊的:奇偶)来实现。

时间优化 & 时间和空间一起优化的(综合优化)

单调队列优化 DP

作用:去除多余点 来 快速寻找决策点。

状态转移方程:

fi=minlijrifj

  • 可能还有 只与 i 有关的数值、其他只与 j 有关的数值 和 常数 参与运算。总之这些都是定值(j 走过了,fj 就成定值了)。
  • maxmin 同理,这里以 min 为例。
  • liri 都随 i 增大而不降(这里假定是 f1fn,且 ri<i)。

发现 liri 都是单调不降的,li 右移相当于进队,而 ri 右移相当于出队。于是直接用队列来维护。

前面的点显然会比后面的先出队,那么如果后面的点已经进队了且比前面的点优,这个前面的点就永远不会作为决策点了,于是直接让它出队即可。发现这样的过程形成了一个从前往后单调递增的队列,它就是单调队列。出队的过程其实就是在队尾踢点直到踢不动。队头的点即是决策点。

在线。

斜率优化 DP

作用:去除多余点 来 快速寻找决策点。

单调队列优化 DP 无法处理 ci×cj 这种与 i 相关的和与 j 相关的乘起来的情况。这时就需要斜率优化 DP。

状态转移方程:

fi=min1ji1ai+bj+cicj

  • maxmin 同理。

下面两个方向都是在线(上面方程里和 j 有关的可以换成 fj,总之走过了就变成定值了)。

有两个方向:

1. 李超线段树(维护直线)

应用范围更广,但速度稍慢。

去 min 推式子。

fiai=cjci+bj

y=kx+b

把与 j 相关的作为直线信息,把与 i 相关的作为点的信息(直线 x=

应用范围更广,但修改 2 只 log,查询 1 只 log。

可以放到树上,李超线段树合并。

2. 队列(维护凸壳)

速度较快,但限制更多。

一些细节可能搞忘了,哪天复习来补。

bj=cicj+fiai

y=kx+b

把与 j 相关的作为点的信息,把与 i 相关的作为直线的信息。

相当于拿一根已知斜率的直线去过每个点,看截距的最小值。那么只需要从下往上移动这个直线,看第一个过的点是哪个。

[斜率 单增 / 单减 时,可以用单调队列来维护凸壳。斜率单增且取 min 是维护下凸壳,斜率单减且取 max 是维护上凸壳。总之就是考虑斜率单增还是单减,取 max 还是取 min,四种情况,画图(也许也可以在脑子里想象出图)分析。](?)

[斜率没有单调性的时候也可能可以,只要点的横坐标有单调性就可以用队列维护凸壳,找决策点时在凸壳上二分。也要注意思考是上凸壳还是下凸壳。](?)

[实现细节上,队列要保证一定有一个点在里面。](?)

[要注意开始的时候那个位置 0 的取值,不一定直接是 0,要为了之后得到正确的值而取值。](?)

还有关于精度、[0](?????;斜率?????)的问题,待补。

听 xjy 说推出来的式子可以不止一种,只要斜率单调即可。

单调队列优化 DP、斜率优化 DP 的观察技巧

  • 拆式子,变成能进行这两种优化的形式。
  • [换 维度枚举顺序。](?)

2024.?.?
2024.10.23

posted @   huangkxQwQ  阅读(17)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 清华大学推出第四讲使用 DeepSeek + DeepResearch 让科研像聊天一样简单!
· 推荐几款开源且免费的 .NET MAUI 组件库
· 实操Deepseek接入个人知识库
· 易语言 —— 开山篇
· Trae初体验
点击右上角即可分享
微信分享提示