【学习笔记】决策单调性优化DP
背景
GDCPC还在发力,清华出题组出的牛客还是 4 题。
这次没有min25筛,不然我能5题(bushi
除了一道用 prufer 序列的恶心 DP 外,还有一道DP题是一个状态难想,并且还需要决策单调性优化的DP,被认为是偏简单的银牌题。
先来看个相对简单的问题
鸡蛋掉落
这是一道非常经典的面试题。本博客不会介绍这题的最优方法(时间复杂度 O ( n ) O(\sqrt n) O(n))
暴力DP
设 f i , j f_{i,j} fi,j 为还剩 i i i 个鸡蛋,楼高 j j j 层,需要的最少实验次数。
显然有转移:
f i , j = min { max ( f i − 1 , w − 1 + 1 , f i , j − w + 1 ) } , 1 ≤ w ≤ j f_{i,j} = \min\{\max (f_{i-1,w-1}+1,f_{i,j-w}+1)\}, 1 \leq w \leq j fi,j=min{max(fi−1,w−1+1,fi,j−w+1)},1≤w≤j
我们称这种问题为 m i n m a x minmax minmax 问题
时间复杂度 O ( k n log n ) O(kn\log n) O(knlogn)
优化1
显然,如果鸡蛋足够多,我们可以直接二分出高度。所以当 k > log n k>\log n k>logn 时可以令 k = log n k = \log n k=logn
优化2
考虑决策单调性。
一个很显然的结论:
- i i i 相同时, j j j 越小, f f f 越小
也就是说:
- f i − 1 , w − 1 f_{i-1,w-1} fi−1,w−1 关于 w w w 单调递增
- f i , j − w f_{i,j-w} fi,j−w 关于 w w w 单调递减
所以两个函数值的关系如图:
我们的最优决策点在红色点那里。显然,这玩意可以二分。
时间复杂度 O ( n log 2 n ) O(n \log ^2 n) O(nlog2n)
class Solution {
public:int superEggDrop(int k, int n) {vector dp(k+1,vector<int>(n+1));for(int i=1; i<=n; i++){dp[1][i]=i;}for(int i=2; i<=k; i++){for(int j=1; j<=n; j++){int l=1,r=j,pos=-1;while(l<=r){int mid=l+r>>1;int x=dp[i-1][mid-1],y=dp[i][j-mid];if(x==y){pos=mid;break;}else if(x<y)l=mid+1;elser=mid-1;}if(pos!=-1)dp[i][j]=max(dp[i-1][pos-1],dp[i][j-pos]);else{dp[i][j]=1e9;pos=l;if(pos>0&&pos<=j) dp[i][j]=max(dp[i-1][pos-1],dp[i][j-pos]);pos=r;if(pos>0) dp[i][j]=min(dp[i][j],max(dp[i-1][pos-1],dp[i][j-pos]));}dp[i][j]++;}}return dp[k][n];// cout<<dp[k][n]<<"\n";}
};
优化3
回到DP式子
f i , j = min { max ( f i − 1 , w − 1 + 1 , f i , j − w + 1 ) } , 1 ≤ w ≤ j f_{i,j} = \min\{\max (f_{i-1,w-1}+1,f_{i,j-w}+1)\}, 1 \leq w \leq j fi,j=min{max(fi−1,w−1+1,fi,j−w+1)},1≤w≤j
当 j j j 增加的时候,最优决策点会发生什么变化?
显然, f i − 1 , w − 1 f_{i-1,w-1} fi−1,w−1 不会变,但是 f i , j − w f_{i,j-w} fi,j−w 是关于 j j j 单调递增的。
不难想象,那个红色的点就会往右边走。也就说,最优决策点也满足单调性,当 j j j 右移时,最优的 w w w 也右移。
所以我们可以用双指针代替二分。
时间复杂度 O ( n log n ) O(n\log n) O(nlogn)
class Solution {
public:int superEggDrop(int k, int n) {vector dp(k+1,vector<int>(n+1));for(int i=1; i<=n; i++){dp[1][i]=i;}for(int i=2; i<=k; i++){int w=1;for(int j=1; j<=n; j++){while(w<j&&dp[i-1][w-1]<dp[i][j-w]){w++;}dp[i][j]=max(dp[i-1][w-1],dp[i][j-w]);if(w>1)dp[i][j]=min(dp[i][j],max(dp[i-1][w-2],dp[i][j-w+1]));dp[i][j]++;}}return dp[k][n];// cout<<dp[k][n]<<"\n";}
};
其实还有一种很好的写法是:
- 先用当前决策点更新 d p dp dp 值
- 如果决策点右移可以使 d p dp dp 值更优就继续往右移并更新 d p dp dp 值
- 否则就 b r e a k break break
2024牛客暑期多校训练营5 K
暴力
最暴力的想法是区间DP,设 d p l , r dp_{l,r} dpl,r 为已经把答案范围缩小到 [ a l , a r ] [a_l,a_r] [al,ar],还需要多少代价才能确定答案。
但你很快会发现没办法直接区间DP,因为你根本不知道 x x x 在哪。
但是如果我们知道之前我左边问过多少次,右边问过多少次,就可以计算区间扩展产生的代价。
所以我们可以设 d p i , j , x , y dp_{i,j,x,y} dpi,j,x,y 代表已经把答案范围缩小到 [ a l , a r ] [a_l,a_r] [al,ar],之前在区间左边问了 x x x 次,右边问了 y y y 次还需要多少代价。
转移就可以枚举中间点 k k k,令分割点为 p p p,那么转移就是
d p l , r , x , y = min { max ( d p l , p , x , y + 1 + k − a p + ( a r − a p ) × y , d p p + 1 , r , x + 1 , y + ( a p + 1 − a l ) × x + a p + 1 − k ) } dp_{l,r,x,y} = \min\{\max(dp_{l,p,x,y+1}+k-a_p+(a_r- a_p)\times y, dp_{p+1,r,x+1,y}+(a_{p+1}-a_l)\times x+a_{p+1}-k)\} dpl,r,x,y=min{max(dpl,p,x,y+1+k−ap+(ar−ap)×y,dpp+1,r,x+1,y+(ap+1−al)×x+ap+1−k)}
时间复杂度 O ( n 4 × 值域 ) O(n^4\times值域) O(n4×值域)
优化1
思考一下,我们真的需要知道两边各询问了多少次吗?
假设 x > y x>y x>y 那么询问代价就是 x − y x-y x−y,否则就是 y − x y-x y−x
y y y 的代价可以在DP转移的时候直接记录
x x x 的代价当 x x x 确定下来的时候可以通过 左边询问次数 - 右边询问次数 来计算
所以其实我们只需记录三四维的差值就行。
设 d p l , r , c dp_{l,r,c} dpl,r,c 代表已经把答案范围缩小到 [ a l , a r ] [a_l,a_r] [al,ar],之前在区间左边和右边询问次数之差为 c c c 次, x x x 的全局代价计算 + 还需要的代价。
显然初始化为 d p i , i , c = a i × c dp_{i,i,c} = a_i\times c dpi,i,c=ai×c
同样的,转移就可以枚举中间点 k k k,令分割点为 p p p,那么转移就是
d p l , r , c = min { max ( d p l , p , c − 1 + k , d p p + 1 , r , c + 1 − k ) } dp_{l,r,c} = \min\{\max(dp_{l,p,c-1}+k, dp_{p+1,r,c+1}-k)\} dpl,r,c=min{max(dpl,p,c−1+k,dpp+1,r,c+1−k)}
时间复杂度 O ( n 3 × 值域 ) O(n^3\times 值域) O(n3×值域)
优化2
可证明, c c c 不会超过 O ( log n ) O(\log n) O(logn) 个,我不会证()
时间复杂度 O ( n 2 log n × 值域 ) O(n^2\log n\times 值域) O(n2logn×值域)
优化3
首先,值域那玩意大的离谱。但是从 d p dp dp 式子很容易看出来,一个 + k +k +k 一个 − k -k −k,显然是有单调性的, k k k 的决策点可以 O ( 1 ) O(1) O(1) 求
int get(int l,int r,int pos,int c)
{int L=a[pos]+1,R=a[pos+1];int x=dp[l][pos][c-1]+L,y=dp[pos+1][r][c+1]-L;if(x>=y) return x;int mx=min(R-L,(y-x)>>1);return max(x+mx,y-mx);
}
时间复杂度 O ( n 3 log n ) O(n^3\log n) O(n3logn)
优化4
现在时间复杂度的瓶颈在于枚举 p p p,怎么把这玩意优化掉呢?
当区间左端点不动,右端点增加的时候,显然方程的第一项是不变的,第二项是单调递减的。这个时候把 p p p 往右移动可以让第一项减小,第二项增大。所以最优决策点 p p p 会关于 r r r 单调递增,我们同样可以用双指针来处理决策点。
时间复杂度 O ( n 2 log n ) O(n^2\log n) O(n2logn)
代码
#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N=1e6+7,inf=1e18,C=60,base=30;
vector<vector<vector<int>>> dp,p;
vector<int> a;
int get(int l,int r,int pos,int c)
{int L=a[pos]+1,R=a[pos+1];int x=dp[l][pos][c-1]+L,y=dp[pos+1][r][c+1]-L;if(x>=y) return x;int mx=min(R-L,(y-x)>>1);return max(x+mx,y-mx);
}
void O_o()
{int n;cin>>n;a.assign(n,0);for(int i=1; i<=n; i++) cin>>a[i];dp.assign(n+1,vector<vector<int>>(n+1,vector<int>(C+1,inf)));p.assign(n+1,vector<vector<int>>(n+1,vector<int>(C+1,0)));for(int len=1; len<=n; len++){for(int l=1; l<=n-len+1; l++){int r=l+len-1;for(int c=1; c<C; c++){if(l==r){dp[l][r][c]=a[l]*(c-base);p[l][r][c]=l;}else{int pos=p[l][r-1][c];dp[l][r][c]=get(l,r,pos,c);while(pos<r-1){int v=get(l,r,pos+1,c);if(v<dp[l][r][c]){pos++;dp[l][r][c]=v;}elsebreak;}p[l][r][c]=pos;}}}}cout<<dp[1][n][base]<<"\n";
}
signed main()
{ios::sync_with_stdio(false); cin.tie(0); cout.tie(0);cout<<fixed<<setprecision(12);int T=1;
// cin>>T;while(T--){O_o();}
}
相关文章:

【学习笔记】决策单调性优化DP
背景 GDCPC还在发力,清华出题组出的牛客还是 4 题。 这次没有min25筛,不然我能5题(bushi 除了一道用 prufer 序列的恶心 DP 外,还有一道DP题是一个状态难想,并且还需要决策单调性优化的DP,被认为是偏简单…...

【每日一题】【二分图最大匹配】【经典板子题】有大家喜欢的零食吗 河南萌新联赛2024第(一)场:河南农业大学 C题 C++
河南萌新联赛2024第(一)场:河南农业大学 C题 有大家喜欢的零食吗 题目描述 在某幼儿园中共有 n n n个小朋友,该幼儿园的老师为这 n n n 个小朋友准备了 n n n 份不一样的零食大礼包。每个小朋友只能选择一个,但老…...

【python】OpenCV—Image Colorization
文章目录 1、CIELAB 色彩空间2、作色问题定义3、Caffe 模型4、代码实现——Image5、代码实现——Video6、参考 1、CIELAB 色彩空间 Lab颜色空间,也称为Lab色彩空间或CIELAB色彩空间,是一种基于人类视觉感知特性的颜色模型。它是在1931年国际照明委员会&…...

vue 学习笔记
模板语法 1. 插值语法 用于解析标签体内容 { { 表达式 } } ,可以直接读取到 data 中的所有属性 2. 指令语法 解析标签(标签属性, 标签内容, 绑定事件) v-bind : href " url " 或 : href &…...
武汉流星汇聚:‘中国制造’闪耀欧洲站,体育赛事成亚马逊增长点
随着2024年的欧洲体育赛事激情四溢,欧洲杯与奥运会的双重盛会不仅点燃了全球体育迷的热情,更为亚马逊欧洲站带来了前所未有的发展机遇。在这场体育盛宴的推动下,欧洲站正展现出其无限的发展潜力和广阔的市场前景,为中国卖家乃至全…...

RPA是什么?探讨RPA发展的最新趋势 | RPA研究
随着人工智能和自动化技术的飞速发展,机器人流程自动化(Robotic Process Automation,简称RPA)正逐渐成为企业数字化转型的关键工具。RPA通过模拟人类用户的操作行为,自动化执行重复性高、规则性强的任务,从…...
sqlalchemy时间范围查询
1、sqlalchemy时间范围查询 在 SQLAlchemy 中,进行时间范围查询可以通过比较日期或时间字段来实现。假设你有一个模型 Event,它包含一个 timestamp 字段,你想查询在某个时间范围内的所有事件。以下是如何使用 SQLAlchemy 来实现这个查询的示例。 首先,确保你有 SQLAlchem…...

电脑不小心删除的文件怎么恢复?教你文件恢复的绝招
在日常使用电脑的过程中,我们有时会因为误操作或不小心而删除了重要的文件。面对这种情况,很多人可能会感到焦虑和无助。但其实,通过一些专业的方法和工具,我们有可能恢复这些被误删的文件。本文将介绍两种常见的恢复方法…...
stm32:使用和学习--硬件和程序
一硬件 1. GPIO 1.FT, TT功能 ft:five tolerate tt:three tolerate 1. FT(Five-Volt Tolerant)引脚 FT 引脚能够容忍高于 VDD 的输入电压(例如 5V)。这些引脚通常不具有连接到 VDD 的保护二极管&…...

ARM知识点二
一、指令 指令的生成过程 指令执行过程示例 if (a 0) {x 0; } else {x x 3; } //翻译为 cmp r0,#0 MOVEQ R1,#0 ADDGT R1,R1,#3指令获取:从Flash中读取 CMP R0, #0,控制器开始执行。 指令解码:解码器解析 CMP 指令,ALU比较R…...
C# ?的使用
栏目总目录 可空类型标记符(?) 说明: 可空类型标记符?用于指示某个值类型(如int、float等)可以为null。这是C# 2.0引入的一个特性,用于处理数据库查询、JSON解析等场景中可能出现的空值。 示例代码&am…...

【unity小技巧】unity性能优化以及如何进行性能测试
文章目录 前言GPU性能优化打包素材 CPU性能优化代码执行优化 性能测试Vector2.Distance 和 sqrMagnitude哪个好?动画切换优化shader属性优化 URP渲染器资产优化对象池优化删除没必要的空函数图片、音乐音效、贴图等素材压缩ScriptableObject优化参数参考完结 前言 …...
算法参考改进点/知识点
1、clip文章中改进点 图像编码器image encoder: 将全局平均池化层替换为注意力池化机制。注意力池化机制:通过一个单层的“transformer式”多头QKV注意力,其中查询query是基于图像的全局平均池表示。改进VIT(Vision Transformer…...

electron 配置、打包 -报错解决
目录 一、配置途中遇到的问题: 二、 make 配置好后开始打包 三、Electron-builder 打包报错 一、配置途中遇到的问题: 1. 安装 yarn add electron -D 一直卡在这里失败 一直卡可以使用下面这个,然后再重新装依赖 1. 采用新的镜像地址 npm …...
基于STM32设计的智能鱼缸(华为云IOT)(200)
文章目录 一、前言1.1 项目介绍【1】项目功能介绍【2】设计实现的功能【3】项目硬件模块组成1.2 设计思路【1】整体设计思路【2】ESP8266工作模式配置【3】自动换水原理1.3 项目开发背景【1】选题的意义【2】可行性分析【3】参考文献1.4 开发工具的选择【1】设备端开发【2】上位…...

Django与数据库
目录 创建项目app 路由子表 数据库 创建数据库 什么是ORM 定义数据库表 Django Admin 管理数据 过滤条件 代码直接生成HTML 使用模板 前后端分离架构 对资源的增删改查处理 列出客户 添加客户 临时取消 CSRF 校验 修改客户信息 删除客户 Django中ORM的处理 数据模…...
大数据系列之:CentOS7安装R详细步骤
大数据系列之:CentOS7安装R详细步骤 一、下载R二、解压R三、创建安装目录四、指定安装目录五、安装编译依赖六、编译与编译安装七、设置环境变量八、激活环境变量九、执行R命令十、执行demo测试程序 一、下载R wget https://cran.r-project.org/src/base/R-4/R-4.4…...

Linux学习第57天:Linux PWM驱动实验
Linux版本号4.1.15 芯片I.MX6ULL 大叔学Linux 品人间百味 思文短情长 本章的思维导图如下: 一、PWM驱动简析 1、设备树下的PWM控制节点 8 路 PWM 都属于 I.MX6ULL 的 AIPS-1 域,分为了两部分, PWM1~P…...
git 远程拉取指定文件
指定操作 git init 创建一个空的文件 git remote add orgin 远程仓库地址链接 表示添加远程库的地址 git config core.sparsecheckout true 打开sparsecheckout功能 注意:如果需要分支内所有文件,这个指令可以直接过忽略,则会拉取对应分支所有的文件…...

【css】 CSS3+JS做一个酷炫的仪表进度条3d进度条
创建一个动态进度环组件 在现代网页设计中,进度环是一种常见的视觉元素,用于展示任务的完成度或加载状态。本文将介绍如何使用Vue.js和Less创建一个动态进度环组件,该组件不仅具有美观的视觉效果,还能够根据用户输入动态改变颜色…...

手游刚开服就被攻击怎么办?如何防御DDoS?
开服初期是手游最脆弱的阶段,极易成为DDoS攻击的目标。一旦遭遇攻击,可能导致服务器瘫痪、玩家流失,甚至造成巨大经济损失。本文为开发者提供一套简洁有效的应急与防御方案,帮助快速应对并构建长期防护体系。 一、遭遇攻击的紧急应…...

相机Camera日志实例分析之二:相机Camx【专业模式开启直方图拍照】单帧流程日志详解
【关注我,后续持续新增专题博文,谢谢!!!】 上一篇我们讲了: 这一篇我们开始讲: 目录 一、场景操作步骤 二、日志基础关键字分级如下 三、场景日志如下: 一、场景操作步骤 操作步…...
镜像里切换为普通用户
如果你登录远程虚拟机默认就是 root 用户,但你不希望用 root 权限运行 ns-3(这是对的,ns3 工具会拒绝 root),你可以按以下方法创建一个 非 root 用户账号 并切换到它运行 ns-3。 一次性解决方案:创建非 roo…...
Unit 1 深度强化学习简介
Deep RL Course ——Unit 1 Introduction 从理论和实践层面深入学习深度强化学习。学会使用知名的深度强化学习库,例如 Stable Baselines3、RL Baselines3 Zoo、Sample Factory 和 CleanRL。在独特的环境中训练智能体,比如 SnowballFight、Huggy the Do…...

tree 树组件大数据卡顿问题优化
问题背景 项目中有用到树组件用来做文件目录,但是由于这个树组件的节点越来越多,导致页面在滚动这个树组件的时候浏览器就很容易卡死。这种问题基本上都是因为dom节点太多,导致的浏览器卡顿,这里很明显就需要用到虚拟列表的技术&…...
Redis:现代应用开发的高效内存数据存储利器
一、Redis的起源与发展 Redis最初由意大利程序员Salvatore Sanfilippo在2009年开发,其初衷是为了满足他自己的一个项目需求,即需要一个高性能的键值存储系统来解决传统数据库在高并发场景下的性能瓶颈。随着项目的开源,Redis凭借其简单易用、…...
MinIO Docker 部署:仅开放一个端口
MinIO Docker 部署:仅开放一个端口 在实际的服务器部署中,出于安全和管理的考虑,我们可能只能开放一个端口。MinIO 是一个高性能的对象存储服务,支持 Docker 部署,但默认情况下它需要两个端口:一个是 API 端口(用于存储和访问数据),另一个是控制台端口(用于管理界面…...

pikachu靶场通关笔记19 SQL注入02-字符型注入(GET)
目录 一、SQL注入 二、字符型SQL注入 三、字符型注入与数字型注入 四、源码分析 五、渗透实战 1、渗透准备 2、SQL注入探测 (1)输入单引号 (2)万能注入语句 3、获取回显列orderby 4、获取数据库名database 5、获取表名…...
vue3 daterange正则踩坑
<el-form-item label"空置时间" prop"vacantTime"> <el-date-picker v-model"form.vacantTime" type"daterange" start-placeholder"开始日期" end-placeholder"结束日期" clearable :editable"fal…...
微服务通信安全:深入解析mTLS的原理与实践
🔥「炎码工坊」技术弹药已装填! 点击关注 → 解锁工业级干货【工具实测|项目避坑|源码燃烧指南】 一、引言:微服务时代的通信安全挑战 随着云原生和微服务架构的普及,服务间的通信安全成为系统设计的核心议题。传统的单体架构中&…...