
动态规划
算法
风萧萧兮易水寒丶
985软件工程本科在读
展开
-
Codeforces Cow and Message(字符串、dp)
题目大意:给定一个由小写字符组成的字符串,求字符串中出现最多的子序列的出现次数解题思路:由题意我们思考可以得到,出现次数最多的子序列必定是长度为2或者1的子序列,长度大于2且出现次数超过长度为2的子序列的出现次数的情况是不存在的,例如abcabc代码:#include <bits/stdc++.h>using namespace std;#define ll long ...原创 2020-04-25 10:30:17 · 175 阅读 · 0 评论 -
Codeforces Hard problem(dp、字符串)
题目大意:给定n个子字符串,对其中若干个字符串进行反转,每次反转产生代价Ci,最后使得字符串按照字典序排列,求最小代价和,不需要反转时输出-1解题思路:首先使字符串的两个状态,正序和反序,相当于从每两个字符串中选出一个,如果选正序代价为0,如果选反序代价为Ci,求出最终最小代价,定义方程dp[i][j]为当选完第i个状态为j的字符串时的最小代价,则有状态转移方程dp[i][j]=min(...原创 2020-04-24 10:35:09 · 263 阅读 · 0 评论 -
Codeforces Boredom(dp)
题目大意:给定一个数组,从中删除数字,如果一次操作为删除k,则k-1和k+1也被删除,此次操作的得分为k,问当数组中的数完全被删除时最高得分为多少解题思路:考虑到an的范围,可以令arr[i]为操作到数i时的最大得分,则有arr[i]=max(arr[i-2]+arr[i],arr[i-1])代码:#include <bits/stdc++.h>#define ll lo...原创 2020-04-23 22:09:17 · 294 阅读 · 0 评论 -
Music problem
解题思路:代码:#include <bits/stdc++.h>using namespace std;int arr[150000];int dp[3610],temp[3610];int main(){ int n,t; cin>>t; while(t--) { scanf("%d",&n); ...原创 2020-04-16 15:59:15 · 274 阅读 · 0 评论 -
武大Shopee杯-A(动态规划)
题目大意:给定n个字符串,从中依次选若干个,头尾相接的两个字符串必须第一个字符串的最后一个字符和第二个字符串的第一个字符相同,求能够组成的最大字符串的长度,目标字符串首尾字符必须相同。解题思路:dp[i][j]为以i为首以j为尾的最大字符串长度,则如果当前字符串为abcde,遍历dp[i][‘a’],如果这个不为0,则转移dp[i][‘e’]=max(dp[i][‘e’],dp[i][‘...原创 2020-04-12 23:01:27 · 233 阅读 · 0 评论 -
树上删边
#include <bits/stdc++.h>using namespace std;#define ll long longconst int maxn=1e5+10;ll head[maxn],n,m,s,cnt,du[maxn];ll dp[maxn];struct Edge{ ll next,to,w;}edge[maxn<<1];l...原创 2020-04-03 21:22:57 · 258 阅读 · 0 评论 -
操作集锦(动态规划、字符串)
代码:#include<bits/stdc++.h>using namespace std;const int mod=1e9+7;#define ll long longll dp[1010][1010],n,k,pre[1010];char s[1010];int main(){ cin>>n>>k; cin>>s+1;...原创 2020-03-28 13:25:51 · 166 阅读 · 0 评论 -
树上子链(树形DP)
解题思路:定义dp[i],代表该子树中最大的一条链(由叶子到根),注意到有可能叶子的权全是复数,所以我们把res初始化为负无穷。核心代码:void dfs(int u,int f){ dp[u]=w[u]; for(auto to:e[u]) { if(to==f) continue; dfs(to,u); res=max(res,dp[u]+dp[to]);//两个子...原创 2020-03-25 15:41:30 · 424 阅读 · 0 评论 -
洛谷—P1809 过河问题(经典动态规划问题)
解题思路:这一题运用的是贪心思想,不能想出,每一步的最优解存在于两种方案中,第一种是过河最短时间的人开船过来,接走一个过河时间最长的人再开船返回。第二种是过河时间最短的人开船过来,他留下,让当前两个最长过河时间的人乘船过岸,然后再让对岸最短过河时间的人开船过河将他接回。令dp[i]为将前i个人运送过河所需要的最短时间,再列出状态转移方程代码:#include<bits/stdc++...原创 2020-02-28 21:35:31 · 1287 阅读 · 0 评论 -
洛谷—P5020 货币系统(背包问题)
这道题目一开始没想到是个背包问题,后来想到了但是没有优化TL了,原因还是没有深刻理解填表法的过程。80分代码:#include<bits/stdc++.h>using namespace std;int t,n,arr[110];bool dp[25010];int main(){ cin>>t; for(int i=0;i<t;++i) { ...原创 2020-02-27 20:55:46 · 209 阅读 · 0 评论 -
洛谷—P1043 数字游戏(区间DP)
解题思路:这道题我写的状态转移方程是:dp[i][j][k]从i到j的m个合积最优结果dp[i][j][1]=arr[i]+arr[i+1]+…+arr[j]dp[i][j][m]=max(dp[i][j][m],dp[i][k][m-l]*dp[k+1][j][l],dp[i][k][l]*dp[k+1][j][m-l])枚举l从1~m/2容易理解,但是做法不够简练#includ...原创 2020-02-25 19:44:50 · 357 阅读 · 0 评论 -
洛谷—P1233 木棍加工(最长上升子序列)
解题思路:先将木棍按照长度从大到小排序(贪心思想),然后求该排列最小不上升子序列的个数,根据dilworth定理,不下降子序列最小个数等于最大上升子序列的长度。代码:#include<bits/stdc++.h>using namespace std;struct node{ int x,y; };node arr[5005];int n,dp[5005],ans...原创 2020-02-25 15:20:49 · 299 阅读 · 0 评论 -
洛谷—P1541 乌龟棋(多维动态规划)
F[a][b][c][d]:表示你出了a张爬行牌1,b张爬行牌2,c张爬行牌3,d张爬行牌4时的得分#include<iostream>#include<algorithm>#include<stdio.h>#include<cstring>#include<queue>#include<iostream>us...原创 2020-02-16 15:54:20 · 193 阅读 · 0 评论 -
洛谷—P1063 能量项链(区间DP)
#include<iostream>#include<stdio.h>#include<algorithm>#include<cstring>using namespace std;long long dp[220][220],ans;int n,arr[220];int main(){ cin>>n; for(i...原创 2020-02-13 19:13:38 · 234 阅读 · 1 评论 -
洛谷—P1736 创意吃鱼法
解题思路:思路:dp+预处理这道题其实和P1387 最大正方形很像,只不过多了一个预处理罢了s1[i][j]表示(i,j)最多向左(或右)延伸多少个格子,使这些格子中的数都是0(不包括(i,j))s2[i][j]表示(i,j)最多向上延伸多少个格子,使这些格子中的数都是0(不包括(i,j))f[i][j]表以(i,j)为右下(左下)角的最大对角线长度方程:f[i][j]=min(f[...原创 2020-02-12 13:46:58 · 125 阅读 · 0 评论 -
洛谷—P1417 烹调方案(背包问题)
解题思路:如果没有b[i]这个属性的话就是明显的01背包问题。现在考虑相邻的两个物品x,y。假设现在已经耗费p的时间,那么分别列出先做x,y的代价:a[x]-(p+c[x])*b[x]+a[y]-(p+c[x]+c[y])*b[y] (①)a[y]-(p+c[y])*b[y]+a[x]-(p+c[y]+c[x])*b[x] (②)对这两个式子化简,得到①>②的条件是c[x]*b[y]&...原创 2020-02-12 11:51:33 · 253 阅读 · 0 评论 -
洛谷—P1077 摆花(动态规划入门)
解题思路:定义状态方程dp[i][j]为前i种花盆摆放j个的总方案数代码:#include<iostream>using namespace std;const int k = 1000007;int m, n, arr[110],dp[110][110];int main(){ cin >> n >> m; for (int i = 1;...原创 2020-02-10 16:40:54 · 238 阅读 · 0 评论 -
洛谷—P1216 数字三角形(动态规划入门)
解题思路:找到可行的状态转移方程代码:#include<iostream>using namespace std;int dp[1010][1010],arr[1010][1010],n,ans;int max(int a, int b){ return a > b ? a : b;}int main(){ cin >> n; for (i...原创 2020-02-10 11:15:06 · 283 阅读 · 0 评论 -
洛谷—P1004 方格取数(四维动态规划)
我们考虑两个人同时走,就相当于数字三角形。状态转移方程为:f[i][j][k][l]=max(f[i-1][j][k-1][l],f[i-1][j][k][l-1],f[i][j-1][k-1][l],f[i][j-1][k][l-1])+a[i][j]+a[k][l];f[i][j][k][l]=max(f[i−1][j][k−1][l],f[i−1][j][k][l−1],f[i][j−1...原创 2020-02-08 14:10:32 · 245 阅读 · 0 评论 -
洛谷—P1880 石子合并(线性动态规划)
解题思路:石子构成了一个环,所以我们开将数据存储两遍,在枚举长度,列出状态转移方程。在考虑如何递推时,通常考虑如下几个方面:是否能覆盖全部状态?求解后面状态时是否保证前面状态已经确定?是否修改了已经确定的状态?代码:#include<iostream>using namespace std;int f1[300][300], f2[300][300];int su...原创 2020-02-07 21:19:15 · 261 阅读 · 0 评论 -
洛谷—P1616 疯狂的采药(完全背包问题)
#include<iostream>using namespace std;int dp[100010];int value[10010];int Time[10010];int t, n;int max(int a, int b){ return a > b ? a : b;}int ks(int t){ for (int i = 1; i <=...原创 2020-02-07 12:16:30 · 160 阅读 · 0 评论 -
洛谷—P1164 小A点菜(0/1背包问题)
#include<iostream>using namespace std;int n, m;int price[1010];int f[110][10010];int main(){ cin >> n >> m; for (int i = 1; i <= n; ++i) cin >> price[i]; for(int...原创 2020-02-07 12:14:41 · 144 阅读 · 0 评论 -
洛谷—P1060开心的金明(0/1背包问题)
#include<iostream>using namespace std;int m,n;int wight[30];int value[30];int dp[30010];int max(int a, int b){ return a > b ? a : b;}int main(){ cin >> n >> m; for (...原创 2020-02-07 12:12:38 · 103 阅读 · 0 评论 -
洛谷—P1091 合唱队形(线性动态规划/子列问题)
解题思路:这道题根据题意不难理解,其实就是求最长上升子列和最长下降子列。定义f[i]为以第i个人为结尾的最长递增子列长度,则有状态转移方程f[i]=max(f[i],f[i-k])从前往后递推定义x[i]为以第i个人为开始的最长递减子列长度,则有状态转移方程x[i]=max(x[i],x[i+k])从后往前递推则最优解为ans=max(x[i]+f[i])-1代码:#...原创 2020-02-07 12:09:06 · 194 阅读 · 0 评论 -
洛谷—P1140 相似基因(线性动态规划)
题目背景大家都知道,基因可以看作一个碱基对序列。它包含了44种核苷酸,简记作A,C,G,TA,C,G,T。生物学家正致力于寻找人类基因的功能,以利用于诊断疾病和发明药物。在一个人类基因工作组的任务中,生物学家研究的是:两个基因的相似程度。因为这个研究对疾病的治疗有着非同寻常的作用。题目描述两个基因的相似度的计算方法如下:对于两个已知基因,例如AGTGATGAGTGATG和GTTAGGTT...原创 2020-02-07 11:59:37 · 410 阅读 · 0 评论 -
洛谷 —P1280尼克的任务(线性动态规划/DP入门)
题目描述尼克每天上班之前都连接上英特网,接收他的上司发来的邮件,这些邮件包含了尼克主管的部门当天要完成的全部任务,每个任务由一个开始时刻与一个持续时间构成。尼克的一个工作日为N分钟,从第一分钟开始到第N分钟结束。当尼克到达单位后他就开始干活。如果在同一时刻有多个任务需要完成,尼克可以任选其中的一个来做,而其余的则由他的同事完成,反之如果只有一个任务,则该任务必需由尼克去完成,假如某些任务开始时...原创 2020-02-07 11:44:47 · 177 阅读 · 0 评论 -
动态规划 背包问题
0/1背包问题:有N件物品和一个容量为V的背包,第i件物品消耗的容量为Ci,价值为Wi,求解放入哪些物品使背包中总价值最大。仔细想想,这里每个物品只有一个,对于每个物品而言,只有两种选择,装入或不装入,装入记为1,不装入为0,我们不能将物品进行分割,比如只拿半个是不允许的。这就是这个问题被称为0/1背包问题的原因。在选择的过程中,我们每做出一种选择,都会将一种情况分裂成两种,最终我们会得到一...原创 2020-01-29 19:40:37 · 390 阅读 · 0 评论