dp题单——区间dp
一、基本概念
1、链式区间dp
for(int len = 2; len <= n; len++){ //枚举区间长度
for(int i = 1; i + len - 1 <= n; i++){//枚举左边界
int j = i + len - 1; //有边界
for(int k = i; k < j; k ++){ // 中间变量位置
dp[i][j] = min(dp[i][j], dp[i][k] + dp[k][j] + cost[i][j]);
}
}
}
2、环形区间dp:把范围扩大一倍,从f[1][n],f[2][n + 1]中寻找最优解

3、关于区间dp的更新状况
每次对固定区间长度进行更新,更新顺序遵循由小区间到大区间。
二、区间dp适用情况

三、相关题目
1、Zuma
#include<bits/stdc++.h>
using namespace std;
const int N = 510;
int dp[N][N], a[N], n;
//dp[i][j]表示合并区间[i][j]所需要的最少步数
signed main(){
cin >> n;
for(int i = 1; i <= n; i++) cin >> a[i];
memset(dp, 0x3f, sizeof dp);
for(int i = 1; i <= n; i++){
dp[i][i] = 1;
if(a[i] == a[i + 1]) dp[i][i + 1] = 1;
else dp[i][i + 1] = 2;
}
for(int len = 2; len <= n; len++){
for(int i = 1; i + len - 1 <= n; i++){
int j = i + len - 1;
//必须要有j - i > 1,因为j - i == 1这种情况在初始化已经被更新了,且是最优值
//为什么当相等的时候,直接由dp[i+1][j-1]转移过来呢?
//因为区间[i+1,j-1]合并到最后会剩下一个回文串,回文串两端加上相同的字母还是回文串,合并次数不变
if(a[i] == a[j] && j - i > 1) {
dp[i][j] = dp[i + 1][j - 1];
}
for(int k = i; k < j; k++){
dp[i][j] = min(dp[i][j], dp[i][k] + dp[k + 1][j]);
}
}
}
cout << dp[1][n] << endl;
return 0;
}
2、Minimum Triangulation
简单区间dp
#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N = 510;
int dp[N][N], a[N], n;
signed main(){
cin >> n;
memset(dp, 0x3f, sizeof dp);
for(int i = 1; i <= n; i++){//区间内只有一个数或者区间内只有两个数,不能组成三角形
dp[i][i] = 0;
dp[i][i + 1] = 0;
}
for(int len = 2; len <= n; len++){
for(int i = 1; i + len - 1 <= n; i++){
int j = i + len - 1;
for(int k = i; k < j; k++){//其他题目区间是不包含关系,所以是k+1
dp[i][j] = min(dp[i][j], dp[i][k] + dp[k][j] + i * k * j);
}
}
}
cout << dp[1][n] << endl;
return 0;
}
3、Array Shrinking
思路非常棒的一道题,代码量比较小,不好想
#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N = 510;
int dp[N][N], a[N], n;//dp表示区间长度(即区间内所剩余的数的个数)
int v[N][N];//记录区间[i][j]合并后所剩的一个数的值(如果可以)
signed main(){
cin >> n;
for(int i = 1; i <= n; i++) {
cin >> a[i];
v[i][i] = a[i];//注意这个敌方的初始化
}
memset(dp, 0x3f, sizeof dp);
for(int i = 1; i <= n; i++){
for(int j = i; j <= n; j++){
dp[i][j] = j - i + 1;//求区间长度
}
}
for(int len = 2; len <= n; len++){
for(int i = 1; i + len - 1 <= n; i++){
int j = i + len - 1;
for(int k = i; k < j; k++){
dp[i][j] = min(dp[i][j], dp[i][k] + dp[k + 1][j]);
if(dp[i][k] == 1 && dp[k + 1][j] == 1 && v[i][k] == v[k + 1][j]){//合并条件还是蛮好理解的
dp[i][j] = 1;
v[i][j] = v[i][k] + 1;
}
}
}
}
cout << dp[1][n] << endl;
return 0;
}
4、Clear the String
这个状态转移方程写的太妙了!爱了爱了。

5、矩阵取数游戏

参考博客:
1、https://www.cnblogs.com/ljy-endl/p/11610549.html
2、https://blog.csdn.net/Gonhz/article/details/105361300
3、https://www.luogu.com.cn/problem/solution/CF1132F
4、https://blog.csdn.net/m0_57344422/article/details/118085490
dp题单——区间dp的更多相关文章
- CSU 1592 石子合并 (经典题)【区间DP】
<题目链接> 题目大意: 现在有n堆石子,第i堆有ai个石子.现在要把这些石子合并成一堆,每次只能合并相邻两个,每次合并的代价是两堆石子的总石子数.求合并所有石子的最小代价. Input ...
- Tinkoff Challenge - Elimination Round D. Presents in Bankopolis(区间DP)
http://codeforces.com/contest/793/problem/D 题意:给出一些点和他们之间的距离,是有向的,这些点从1~n顺序排列,现在选出k个点组成一条路径,使他们之间的距离 ...
- poj 2955 Brackets (区间dp基础题)
We give the following inductive definition of a “regular brackets” sequence: the empty sequence is a ...
- 「区间DP」「洛谷PP3146 」[USACO16OPEN]248 G
[USACO16OPEN]248 G 题目: 题目描述 Bessie likes downloading games to play on her cell phone, even though sh ...
- 区间dp总结
poj 1141 Brackets Sequence 基础的区间dp题,注意dp边缘的初始化,以及递归过程中的边界 poj 2955 Brackets 依旧注意初始化,水题 hdu 4745 Two ...
- LightOJ1031 Easy Game(区间DP)
我可能真想不到这题是区间DP,不过知道是区间DP想了下就AC了. dp[i][j]表示局面为ai...aj先手能获得与后手得分的最大差值 那么转移到当前状态就是枚举中间的位置,分成两边,其中一边先手全 ...
- 区间DP,数位DP
dp(动态规划)顾名思义便是动态的一种规划,而这种规划往往会跟状态,状态转移方程,记忆化搜索扯上关系,当然DP也是各个OI考试的必考点和常考点,在毒瘤出题人的折磨下,出现了许许多多的动态规划,有线性, ...
- P1040 加分二叉树 区间dp
题目描述 设一个nn个节点的二叉树tree的中序遍历为(1,2,3,…,n1,2,3,…,n),其中数字1,2,3,…,n1,2,3,…,n为节点编号.每个节点都有一个分数(均为正整数),记第ii个节 ...
- HDU4632 Poj2955 括号匹配 整数划分 P1880 [NOI1995]石子合并 区间DP总结
题意:给定一个字符串 输出回文子序列的个数 一个字符也算一个回文 很明显的区间dp 就是要往区间小的压缩! #include<bits/stdc++.h> using namesp ...
- 直线石子合并(区间DP)
石子合并 时间限制:1000 ms | 内存限制:65535 KB 描述有N堆石子排成一排,每堆石子有一定的数量.现要将N堆石子并成为一堆.合并的过程只能每次将相邻的两堆石子堆成一堆,每次合并花费 ...
随机推荐
- Redis不同版本性能研究
Redis不同版本性能研究 背景 前期同事遇到了一个大key的慢查询. 前提条件是: 一个 60万key的环境里面. 有一个 260万元素的set类型的key 产品经常会进行 smember key ...
- 阿里云ECS自建K8S_IPV6重启后异常问题解决过程
阿里云ECS自建K8S_IPV6重启后异常问题解决过程 背景 最近安装了一个单节点的K8S_IPV6 昨天不知道何故 突然宕机了. 然后只能在阿里云的控制台后台重启了ECS 启动之后看K8S的状态一开 ...
- [转帖]配置cri-docker使kubernetes1.24以docker作为运行时
从kubernetes 1.24开始,dockershim已经从kubelet中移除,但因为历史问题docker却不支持kubernetes主推的CRI(容器运行时接口)标准,所以docker不能再作 ...
- [转帖]DBWR与LGWR的写入机制
https://www.jianshu.com/p/6c87cb6cd320 读与写是每个数据库提供的最基本的功能.当数据库中出现第一个进程时,总免不了要将数据从磁盘上加载到内存中,一次数据库的物理I ...
- [转帖]比 Python 快 35000 倍!LLVM&Swift 之父宣布全新编程语言 Mojo:编程被颠覆了
https://www.infoq.cn/article/GFfVLVpkIGOcKYB85Opb "Mojo 可能是近几十年来最大的编程语言进步." 近日,由 LLVM 和 Sw ...
- 超级好用的elementui动态循环菜单
<template> <div> <el-menu @select="selectMenu" :default-active="curren ...
- 如何用etcdctl产生分布式环境中的递增ID
作者:张富春(ahfuzhang),转载时请注明作者和引用链接,谢谢! cnblogs博客 zhihu Github 公众号:一本正经的瞎扯 用golang代码当然很简单,我这里是在shell环境中, ...
- JS ----- Javascript中apply、call、bind
这篇文章实在是很难下笔,因为网上相关文章不胜枚举. 巧合的是前些天看到阮老师的一篇文章的一句话: "对我来说,博客首先是一种知识管理工具,其次才是传播工具.我的技术文章,主要用来整理我还不懂 ...
- 紫 distance
仅此纪念我爆掉的T3 紫,即RE,运行出错,梦幻,而又不失杀气 根据<雪distance>改编,分为提交前,评测前,评测时,评测后 你说我考试AK,可我却运行出错 任凭无尽的懊悔将我淹没, ...
- 46从零开始用Rust编写nginx,数据还能这么传,多层代理(IP多级代理)搭建
wmproxy wmproxy已用Rust实现http/https代理, socks5代理, 反向代理, 负载均衡, 静态文件服务器,websocket代理,四层TCP/UDP转发,内网穿透等,会将实 ...