动态规划原理
基本思想: 问题的最优解可以有子问题的最优解推导得到,可以先求子问题的最优解,再构造原问题的最优解。如果子问题有较多的重复出现,则可以自底向上从最终子问题向原问题逐步求解。适合于用动态规划求解的问题,经分解得到子问题往往不是互相独立的。对于有些子问题被重复计算了很多次,我们能够保存已解决的子问题的答案,在需要时再找出已求得的答案,这样就可以避免大量的重复计算,节省时间。我们可以用一个表来记录所有已解的子问题的答案。不管该子问题以后是否被用到,只要它被计算过,就将其结果填入表中。这就是动态规划法的基本思路。
动态规划算法的设计步骤:
1、分析优化解的结构
2、递归的定义最优解的代价
3、自底向上的计算优化解的代价并保存,并获取构造最优解的信息
4、根据构造最优解的信息构造最优解
基本模型:
(1)确定问题的决策对象。
(2)对决策过程划分阶段。
(3)对各阶段确定状态变量。
(4)根据状态变量确定费用函数和目标函数。
(5)建立各阶段状态变量的转移过程,确定状态转移方程。
状态转移方程的一般形式:
一般形式:
U:状态; X:策略
顺推:f[Uk]=opt{f[Uk-1]+L[Uk-1,Xk-1]} 其中, L[Uk-1,Xk-1]: 状态Uk-1通过策略Xk-1到达状态Uk 的费用 初始f[U1];结果:f[Un]。
倒推:
f[Uk]=opt{f[Uk+1]+L[Uk,Xk]}
L[Uk,Xk]: 状态Uk通过策略Xk到达状态Uk+1 的费用
初始f[Un];结果:f(U1)
动态规划的简单应用-最长公共子序列
整体思想就是,申请一个二维的数组初始化为 0,然后判断对应的字符是否相等,相等的话
arr[i ][j]= arr [ i - 1 ][ j - 1] + 1 。
当 i = 0 或者 j = 0 的时候单独分析,字符相等的话 arr [ i ][ j ] 就赋为 1 。
arr [ i ][ j ] 保存的就是公共子串的长度。
public String longestString(String s1,String s2) {
int len1=s1.length();
int len2=s2.length();
int [][] arr=new int[len1][len2];
int maxLen=0;
int maxEnd=0;
for(int i=0;i<len1;i++) {
for(int j=0;j<len2;j++) {
if(s1.charAt(i)==s2.charAt(j)) {
if(i==0 || j==0) {
arr[i][j]=1;
}else {
arr[i][j]=arr[i-1][j-1]+1;
}
}
if(arr[i][j]>maxLen) {
maxLen=arr[i][j];
maxEnd=i;
}
}
}
return s1.substring(maxEnd-maxLen+1,maxEnd+1);
}
来源:CSDN
作者:——铎
链接:https://blog.csdn.net/weixin_43729960/article/details/104570222