算法第三章作业
以“单调递增最长子序列”为例
题目
3-2 单调递增最长子序列 (25分)
设计一个O(n2)时间的算法,找出由n个数组成的序列的最长单调递增子序列。
输入格式:
输入有两行: 第一行:n,代表要输入的数列的个数 第二行:n个数,数字之间用空格格开
输出格式:
最长单调递增子序列的长度
输入样例:
在这里给出一组输入。例如:
5
1 3 5 2 9
输出样例:
在这里给出相应的输出。例如:
4
代码
#include<iostream> using namespace std; int n; int array[1000];//用于存储输入的序列 int m[1000];//m【i】表示以第i个元素为结尾的最长单调递增序列的长度 int length;//最长单调递增序列的长度 int FindLongest() { length=m[1]=1; if(n==1) return 1; for(int i=1;i<=n;i++) { //length=m[1]; for(int j=1;j<i;j++) { if(array[j]<array[i]) { m[i]=max(m[i],m[j]+1);//如果m[j]+1比比原来的m[i]要大,则更新m[i] } } if(length<m[i]) length=m[i];//更新单调递增的序列长度 } return length; } int main() { cin>>n; for(int i=1;i<=n;i++) { cin>>array[i]; } cout<<FindLongest(); }
1.1根据最优子结构性质,列出递归方程式
m[i]表示以第i个元素为结尾的最长单调递增序列的长度
m[i]=max(m[i],m[j]+1)
1.2 给出填表法中表的维度、填表范围和填表顺序。
填的表是一维数组,用的二重循环,从上到下(1到n),从左到右(1到 i)
1.3 分析该算法的时间和空间复杂度
根据题目要求,时间复杂度为O(n2)
空间复杂度为n,用到了一维数组存储
2. 你对动态规划算法的理解
动态规划将原问题分解为多个子问题,具有最优子结构性质和重叠子问题,通过填表法,避免了子问题重复求解的问题,提高了算法的效率。
需要对问题进行分析,确定出递归方程式,然后确定填表顺序,维度,范围等,分析清楚后,代码就更加容易写出来了。
3. 说明结对编程情况
上周上机课,答的题目是最低通行费问题,我开始没有什么思路,然后是搭档先想到了解题思路,打出的代码也运行通过了,然后她耐心给我讲解,原本不太懂动态规划的我听了之后好像一下子就明白了。