实验三动态规划

合集下载

实验三 动态规划

实验三 动态规划

实验三动态规划(一)、实验目的通过编程实现动态规划的有关算法,理解动态规划的原理,掌握动态规划基本思想与应用技巧。

(二)、实验题目与要求:实验题目1:最长公共子序列问题的算法若给定序列X={x1,x2,…,xm},则另一序列Z={z1,z2,…,zk}是X的子序列是指存在一个严格递增下标序列{i1,i2,…,ik}使得对于所有j=1,2,…,k有:zj=xij。

例如,序列Z={B,C,D,B}是序列X={A,B,C,B,D,A,B}的子序列,相应的递增下标序列为{2,3,5,7}。

给定2个序列X和Y,当另一序列Z既是X的子序列又是Y的子序列时,称Z是序列X 和Y的公共子序列。

给定2个序列X={x1,x2,…,xm}和Y={y1,y2,…,yn},找出X和Y的最长公共子序列。

实验要求:1.理解动态规划算法的原理,认真阅读题目。

完善程序,实现该算法;2.输入:X序列为xyxzyxyzzy, Y序列为xzyzxyzxyzxy输出:二维数组c、最长公共子序列。

实验提示:1)先求最长公共子序列,X和Y的最长公共子序列的长度记录于c[m][n]中public static int lcsLength(char [ ]x,char [ ]y,int [ ][ ]b){ int m=x.length-1;int n=y.length-1;int [][]c=new int [m+1][n+1];for (int i = 1; i <= m; i++) c[i][0]=0;for (int i = 1; i <= n; i++) c[0][i]=0;for (int i = 1; i <= m; i++)for (int j = 1; j <= n; j++) {if (x[i]= =y[j]) { c[i][j]=c[i-1][j-1]+1; b[i][j]=1;}else if (c[i-1][j]>=c[i][j-1]) { c[i][j]=c[i-1][j]; b[i][j]=2;}else { c[i][j]=c[i][j-1]; b[i][j]=3;}}return c[m][n];}2)然后构造最长公共子序列public static void lcs(int i,int j,char [] x,int [][] b){ if (i = =0 || j= =0) return;if (b[i][j]= = 1){lcs(i-1,j-1,x,b);System.out.print(x[i]);}else if (b[i][j]= = 2) lcs(i-1,j,x,b); else lcs(i,j-1,x,b);}[][][]{}⎪⎩⎪⎨⎧<+++==-<≤j i p p p j k m k i m j i j i m j k i jk i 1,1,min 0,实验题目2:用两台处理机A 和B 处理n 个作业。

动态规划-(矩阵连乘)

动态规划-(矩阵连乘)
} return m[0][n-1]; }
12
4、构造最优解
void MatrixChain::Traceback(int i, int j) {
if(i==j) { cout<<'A'<<i; return;} if (i<s[i][j]) cout<<'('; Traceback(i, s[i][j]); if (i<s[i][j])cout<<')'; if(s[i][j]+1<j)cout<<'('; Traceback(s[i][j]+1, j); if(s[i][j]+1<j) cout<<')'; } void MatrixChain::Traceback() { cout<<'('; Traceback(0, n-1); cout<<')'; cout<<endl; }
②当i=j时,A[i:j]=Ai,因此,m[i][i]=0,i=1,2,…,n ③当i<j时,m [ i ] j ] [ m [ i ] k ] [ m [ k 1 ] j ] [ p i 1 p k p j
这里 A i 的维数为 pi1pi
∴可以递归地定义m[i][j]为:
m [i]j] [ m i k j{ m [i]n k [ ] m [k 0 1 ]j] [ p i 1 p kp j}i i j j
根据MatrixChain动态规划算法: ②计算m[i][j]数乘次数
m[2][5]=min m[2][2]+m[3][5]+p1p2p5=13000

动态规划实验报告

动态规划实验报告

动态规划实验报告动态规划实验报告一、引言动态规划是一种常用的算法设计方法,广泛应用于计算机科学和运筹学等领域。

本实验旨在通过实际案例,探究动态规划算法的原理和应用。

二、实验背景动态规划算法是一种通过将问题分解为子问题,并存储子问题的解来解决复杂问题的方法。

它通常适用于具有重叠子问题和最优子结构性质的问题。

三、实验目的1. 理解动态规划算法的基本原理;2. 掌握动态规划算法的实现方法;3. 分析动态规划算法在实际问题中的应用。

四、实验过程本实验选择了经典的背包问题作为案例进行分析。

背包问题是一个组合优化问题,给定一个背包的容量和一系列物品的重量和价值,如何选择物品放入背包,使得背包中物品的总价值最大化。

1. 确定状态在动态规划算法中,状态是问题的关键。

对于背包问题,我们可以将状态定义为背包的容量和可选择的物品。

2. 确定状态转移方程状态转移方程是动态规划算法的核心。

对于背包问题,我们可以定义一个二维数组dp[i][j],表示在背包容量为j的情况下,前i个物品的最大总价值。

则状态转移方程可以表示为:dp[i][j] = max(dp[i-1][j], dp[i-1][j-w[i]] + v[i])其中w[i]表示第i个物品的重量,v[i]表示第i个物品的价值。

3. 初始化边界条件在动态规划算法中,边界条件是必不可少的。

对于背包问题,边界条件可以定义为当背包容量为0时,无论物品如何选择,总价值都为0。

4. 递推求解根据状态转移方程和边界条件,我们可以通过递推的方式求解问题。

具体步骤如下:- 初始化dp数组;- 逐行逐列计算dp数组的值,直到得到最终结果。

五、实验结果与分析通过实验,我们得到了背包问题的最优解。

同时,我们还可以通过分析dp数组的取值,了解到每个状态下的最优选择。

这为我们提供了在实际问题中应用动态规划算法的思路。

六、实验总结本实验通过对动态规划算法的实际案例进行分析,深入理解了动态规划算法的原理和应用。

实验三-动态规划法求多段图问题

实验三-动态规划法求多段图问题

本科实验报告课程名称:算法设计与分析实验项目:动态规划法求多段图问题实验地点:专业班级:学号:学生姓名:指导教师:实验三动态规划法求多段图问题一、实验目的1.掌握动态规划算法的基本思想2.掌握多段图的动态规划算法3.选择邻接表或邻接矩阵方式来存储图4、分析算法求解的复杂度。

二、实验内容设G=(V,E)是一个带权有向图,其顶点的集合V被划分成k>2个不相交的子集Vi,1<i<=k,其中V1和Vk 分别只有一个顶点s(源)和一个顶点t(汇)。

图中所有边的始点和终点都在相邻的两个子集Vi和Vi+1中。

求一条s到t的最短路线。

参考讲义p136图5-24中的多段图,试选择使用向前递推算法或向后递推算法求解多段图问题。

三、实验环境程序设计语言:c++编程工具:microsoft visual studio 2010四、算法描述和程序代码#include <stdio.h>#include <stdlib.h>#include <conio.h>#include <iostream.h>#define MAX 100#define n 12#define k 5int c[n][n];void init(int cost[]) //初始化图{int i,j;for(i=0;i<13;i++){ for(j=0;j<13;j++){ c[i][j]=MAX;}}c[1][2]=9; c[1][3]=7; c[1][4]=3; c[1][5]=2; c[2][6]=4; c[2][7]=2; c[2][8]=1;c[3][6]=2; c[3][7]=7; c[4][8]=11; c[5][7]=11; c[5][8]=8; c[6][9]=6; c[6][10]=5;c[7][9]=4; c[7][10]=3; c[8][10]=5; c[8][11]=6; c[9][12]=4; c[10][12]=2;c[11][12]=5;}void fgraph(int cost[],int path[],int d[]) //使用向前递推算法求多段图的最短路径{ int r,j,temp,min;for(j=0;j<=n;j++)cost[j]=0;for(j=n-1;j>=1;j--){ temp=0;min=c[j][temp]+cost[temp]; //初始化最小值for(r=0;r<=n;r++){if(c[j][r]!=MAX){if((c[j][r]+cost[r])<min) //找到最小的r{ min=c[j][r]+cost[r];temp=r;} } }cost[j]=c[j][temp]+cost[temp];d[j]=temp; }path[1]=1; path[k]=n;for(j=2;j<k;j++)path[j]=d[path[j-1]];}void bgraph(int bcost[],int path1[],int d[])//使用向后递推算法求多段图的最短路径{ int r,j,temp,min;for(j=0;j<=n;j++)bcost[j]=0;for(j=2;j<=n;j++){ temp=12;min=c[temp][j]+bcost[temp];//初始化最小值for(r=0;r<=n;r++){if(c[r][j]!=MAX){if((c[r][j]+bcost[r])<min) //找到最小的r{min=c[r][j]+bcost[r];temp=r;} } }bcost[j]=c[temp][j]+bcost[temp];d[j]=temp;}path1[1]=1;path1[k]=n;for(int i=4;i>=2;i--){ path1[i]=d[path1[i+1]];} }void main(){int cur=-1;int cost[13],d[12],bcost[13];int path[k];int path1[k];cout<<"\t\t\t动态规划解多段图问题"<<endl;cout<<"\n\n";init(cost);fgraph(cost,path,d);cout<<"输出使用向前递推算法后的最短路径:\n\n";for(int i=1;i<=5;i++){ cout<<path[i]<<" ";}cout<<"\n";cout<<endl<<"最短路径为长度:"<<cost[1]<<endl;cout<<"\n";cout<<"\n输出使用向后递推算法后的最短路径:\n\n";bgraph(bcost,path1,d);for(i=1;i<=5;i++){ cout<<path1[i]<<" ";}cout<<"\n";cout<<endl<<"最短路径为长度:"<<bcost[12]<<endl;cout<<"\n";}五、实验结果截图六、实验总结七、。

动态规划实验报告心得

动态规划实验报告心得

一、实验背景动态规划是一种重要的算法设计方法,广泛应用于解决优化问题。

本次实验旨在通过实际操作,加深对动态规划算法的理解,掌握其基本思想,并学会运用动态规划解决实际问题。

二、实验内容本次实验主要包括以下几个内容:1. 动态规划算法概述首先,我们对动态规划算法进行了概述,学习了动态规划的基本概念、特点、应用领域等。

动态规划是一种将复杂问题分解为若干个相互重叠的子问题,并存储已解决子问题的解,以避免重复计算的方法。

2. 矩阵连乘问题矩阵连乘问题是动态规划算法的经典问题之一。

通过实验,我们学会了如何将矩阵连乘问题分解为若干个相互重叠的子问题,并利用动态规划方法求解。

实验过程中,我们分析了问题的最优子结构、子问题的重叠性,以及状态转移方程,从而得到了求解矩阵连乘问题的动态规划算法。

3. 0-1背包问题0-1背包问题是另一个典型的动态规划问题。

在实验中,我们学习了如何将0-1背包问题分解为若干个相互重叠的子问题,并利用动态规划方法求解。

实验过程中,我们分析了问题的最优子结构、子问题的重叠性,以及状态转移方程,从而得到了求解0-1背包问题的动态规划算法。

4. 股票买卖问题股票买卖问题是动态规划在实际应用中的一个例子。

在实验中,我们学习了如何将股票买卖问题分解为若干个相互重叠的子问题,并利用动态规划方法求解。

实验过程中,我们分析了问题的最优子结构、子问题的重叠性,以及状态转移方程,从而得到了求解股票买卖问题的动态规划算法。

三、实验心得1. 动态规划算法的思维方式通过本次实验,我深刻体会到了动态规划算法的思维方式。

动态规划算法的核心是将复杂问题分解为若干个相互重叠的子问题,并存储已解决子问题的解。

这种思维方式有助于我们更好地理解和解决实际问题。

2. 状态转移方程的重要性在动态规划算法中,状态转移方程起着至关重要的作用。

它描述了子问题之间的关系,是求解问题的关键。

通过本次实验,我学会了如何分析问题的最优子结构,以及如何建立合适的状态转移方程。

动态规划问题实验报告(3篇)

动态规划问题实验报告(3篇)

第1篇一、实验目的本次实验旨在让学生理解动态规划算法的基本概念,掌握动态规划解决问题的基本思想和步骤,并能运用动态规划算法解决实际问题。

通过实验,学生应能够:1. 理解动态规划算法的概念及其应用领域。

2. 掌握动态规划的基本思想和解决问题的基本步骤。

3. 学习动态规划算法设计策略,并能够运用到实际问题中。

4. 通过实际编程,提高编程能力和问题解决能力。

二、实验环境1. 操作系统:Windows 102. 编程语言:Python3.83. 开发环境:PyCharm三、实验内容本次实验选择了三个典型的动态规划问题进行实践:1. 最长公共子序列问题2. 矩阵连乘问题3. 剪绳子问题四、实验步骤1. 最长公共子序列问题(1)问题描述:给定两个序列X和Y,找出X和Y的最长公共子序列。

(2)算法设计:- 使用二维数组dp[i][j]表示X的前i个字符和Y的前j个字符的最长公共子序列的长度。

- 初始化dp[0][j] = 0和dp[i][0] = 0。

- 对于i > 0和j > 0,如果X[i-1] == Y[j-1],则dp[i][j] = dp[i-1][j-1] + 1;否则,dp[i][j] = max(dp[i-1][j], dp[i][j-1])。

(3)代码实现:```pythondef longest_common_subsequence(X, Y):m, n = len(X), len(Y)dp = [[0] (n + 1) for _ in range(m + 1)]for i in range(1, m + 1):for j in range(1, n + 1):if X[i - 1] == Y[j - 1]:dp[i][j] = dp[i - 1][j - 1] + 1else:dp[i][j] = max(dp[i - 1][j], dp[i][j - 1])return dp[m][n]```2. 矩阵连乘问题(1)问题描述:给定n个矩阵A1, A2, ..., An,其中Ai与Ai-1是可乘的,i = 1, 2, ..., n-1。

动态规划实验报告摘要(3篇)

动态规划实验报告摘要(3篇)

第1篇本实验报告针对动态规划算法进行深入研究和实践,旨在通过一系列实验,加深对动态规划思想、基本原理及实际应用的理解。

实验内容涵盖了动态规划算法的多个经典问题,包括找零钱问题、独立任务最优调度问题、最长公共子序列问题、矩阵连乘问题、剪绳子问题以及0-1背包问题等。

一、实验目的1. 理解动态规划算法的概念,掌握动态规划的基本思想和解决问题的基本步骤。

2. 学习动态规划算法设计策略,提高算法设计能力。

3. 通过实际案例,体会动态规划算法在解决实际问题中的应用价值。

二、实验内容与步骤1. 找零钱问题实验要求设计一个动态规划算法,对给定面值的硬币组合,计算出所有可能找零方式的硬币个数。

通过实验,掌握了动态规划算法的基本原理,并熟悉了动态规划在解决组合优化问题中的应用。

2. 独立任务最优调度问题实验要求设计一个动态规划算法,使得两台处理机处理完n个作业的时间最短。

通过实验,了解了动态规划在解决调度问题中的应用,并掌握了多阶段决策问题的求解方法。

3. 最长公共子序列问题实验要求找出两个序列的最长公共子序列。

通过实验,学习了动态规划在解决序列匹配问题中的应用,并掌握了如何通过动态规划算法优化问题求解过程。

4. 矩阵连乘问题实验要求确定计算矩阵连乘积的计算次序,使得所需数乘次数最少。

通过实验,了解了动态规划在解决矩阵连乘问题中的应用,并掌握了如何通过动态规划算法优化计算过程。

5. 剪绳子问题实验要求将一根绳子剪成m段,使得各段乘积最大。

通过实验,掌握了动态规划在解决资源分配问题中的应用,并学会了如何通过动态规划算法找到最优解。

6. 0-1背包问题实验要求用动态规划算法解决0-1背包问题。

通过实验,了解了动态规划在解决背包问题中的应用,并掌握了如何通过动态规划算法优化问题求解过程。

三、实验结果与分析通过对以上问题的动态规划算法实现,实验结果表明:1. 动态规划算法能够有效地解决组合优化问题、调度问题、序列匹配问题、矩阵连乘问题、资源分配问题以及背包问题等。

实验三动态规划算法实验

实验三动态规划算法实验

实验三动态规划算法的应用一、实验目的1.掌握动态规划算法的基本思想,包括最优子结构性质和基于表格的最优值计算方法。

2.熟练掌握分阶段的和递推的最优子结构分析方法。

3.学会利用动态规划算法解决实际问题。

二、实验内容1.问题描述:题目一:数塔问题给定一个数塔,其存储形式为如下所示的下三角矩阵。

在此数塔中,从顶部出发,在每一节点可以选择向下走还是向右走,一直走到底层。

请找出一条路径,使路径上的数值和最大。

输入样例(数塔):912 1510 6 82 18 9 519 7 10 4 16输出样例(最大路径和):59题目二:最长单调递增子序列问题设计一个O(n2)复杂度的算法,找出由n个数组成的序列的最长单调递增子序列。

题目三:Common SubsequenceA subsequence of a given sequence is the given sequence with some elements (possible none) left out. Given a sequence X = <x1, x2, ..., xm> another sequence Z = <z1, z2, ..., zk> is a subsequence of X if there exists a strictly increasing sequence <i1, i2, ..., ik> of indices of X such that for all j = 1,2,...,k, xij = zj. For example, Z = <a, b, f, c> is a subsequence of X = <a, b, c, f, b, c> with index sequence <1, 2, 4, 6>. Given two sequences X and Y the problem is to find the length of the maximum-length common subsequence of X and Y.The program input is from a text file. Each data set in the file contains two strings representing the given sequences. The sequences are separated by any number of white spaces. The input data are correct. For each set of data the program prints on the standard output the length of the maximum-length common subsequence from the beginning of a separate line.输入样例abcfbc abfcabprogramming contestabcd mnp输出样例42题目四 0-1背包问题给定n种物品和一个背包。

实验3动态规划

实验3动态规划

实验3动态规划实验二贪心法(4学时)上机实验一般应包括以下几个步骤:(1)、准备好上机所需的程序。

手编程序应书写整齐,并经人工检查无误后才能上机。

(2)、上机输入和调试自己所编的程序。

一人一组,独立上机调试,上机时出现的问题,最好独立解决。

(3)、上机结束后,整理出实验报告。

实验报告应包括:题目、程序清单、运行结果、对运行情况所作的分析。

一、实验目的与要求1. 掌握动态规划法的基本思想方法;理解动态规划的基本思想,理解动态规划算法的两个基本要素最优子结构性质和子问题的重叠性质。

熟练掌握典型的动态规划问题。

2. 了解适用于用动态规划法求解的问题类型,并能设计相应动态规划法算法;3. 掌握动态规划算法复杂性分析方法分析问题复杂性。

二、实验内容(以下题目要求采用动态规划算法完成):1、找零钱问题设有n 种不同面值的硬币,各硬币的面值存于数组T[1:n]中。

现要用这些面值的硬币来找钱,可以实用的各种面值的硬币个数不限。

当只用硬币面值T[1],T[2],…,T[i]时,可找出钱数j 的最少硬币个数记为C(i,j)。

若只用这些硬币面值,找不出钱数j 时,记C(i,j)=∞。

设计一个动态规划算法,对1≤j ≤L ,计算出所有的C( n,j )。

算法中只允许实用一个长度为L 的数组。

用L 和n 作为变量来表示算法的计算时间复杂性2、最大子段和问题给定由n 个整数组成的序列(a1, a2, …, an),求该序列形如的子段和的最大值,当所有整数均为负整数时,其最大子段和为0。

如序列为(-20,11,-4,13,-5)其最大子段和为20对应子段为(11,-4,13)3、数塔问题有N 件物品和一个容量为V 的背包。

第i 件物品的重量是c[i],价值是w[i]。

求解将哪些物品装入背包可使这些物品的费用总和不超过背包容量,且价值总和最大。

三、实验步骤1.理解算法思想和问题要求;2.编程实现题目要求;3.上机输入和调试自己所编的程序;∑=j i k k a ∑=42k k a4.验证分析实验结果;5.整理出实验报告。

动态规划实验报告

动态规划实验报告

动态规划实验报告《动态规划实验报告》动态规划是一种重要的算法设计技术,它在解决许多实际问题中具有广泛的应用。

本实验报告将介绍动态规划算法的基本原理,并通过一个实际问题的求解过程来展示其应用效果。

首先,我们来了解一下动态规划的基本原理。

动态规划是一种将原问题分解为子问题来求解的方法,它通常用于求解最优化问题。

动态规划算法的核心思想是将原问题分解为若干个子问题,然后通过求解子问题的最优解来得到原问题的最优解。

为了避免重复计算子问题,动态规划算法通常采用记忆化搜索或者自底向上的方式来进行计算。

接下来,我们将通过一个实际问题来展示动态规划算法的应用效果。

假设我们有一组数字,我们希望找到其中的一个子序列,使得这个子序列的和最大。

这个问题可以通过动态规划算法来求解,具体的求解过程如下:1. 定义状态:我们定义一个状态数组dp,其中dp[i]表示以第i个数字结尾的子序列的最大和。

2. 状态转移方程:我们可以通过以下状态转移方程来求解dp数组:dp[i] = max(dp[i-1] + nums[i], nums[i]),其中nums[i]表示第i个数字。

3. 初始状态:我们将dp数组的初始状态设为dp[0] = nums[0]。

4. 求解最优解:最终的最优解即为dp数组中的最大值。

通过以上求解过程,我们可以得到原问题的最优解,即最大子序列的和。

这个实例展示了动态规划算法在实际问题中的应用效果,通过合理的状态定义和状态转移方程,我们可以高效地求解复杂的最优化问题。

综上所述,动态规划算法是一种重要的算法设计技术,它在解决最优化问题中具有广泛的应用。

通过合理的状态定义和状态转移方程,我们可以高效地求解复杂的实际问题。

希望本实验报告能够帮助读者更好地理解动态规划算法的基本原理和应用方法。

动态规划实验报告

动态规划实验报告

动态规划实验报告⼀、问题描述7-3 最低通⾏费 (25 分)⼀个商⼈穿过⼀个N×N的正⽅形的⽹格,去参加⼀个⾮常重要的商务活动。

他要从⽹格的左上⾓进,右下⾓出。

每穿越中间1个⼩⽅格,都要花费1个单位时间。

商⼈必须在(2N-1)个单位时间穿越出去。

⽽在经过中间的每个⼩⽅格时,都需要缴纳⼀定的费⽤。

这个商⼈期望在规定时间内⽤最少费⽤穿越出去。

请问⾄少需要多少费⽤?注意:不能对⾓穿越各个⼩⽅格(即,只能向上下左右四个⽅向移动且不能离开⽹格)。

输⼊格式:第⼀⾏是⼀个整数,表⽰正⽅形的宽度N (1≤N<100);后⾯N⾏,每⾏N个不⼤于100的整数,为⽹格上每个⼩⽅格的费⽤。

输出格式:⾄少需要的费⽤。

输⼊样例:51 4 6 8 102 5 7 15 176 8 9 18 2010 11 12 19 2120 23 25 29 33输出样例:109样例中,最⼩值为109=1+2+5+7+9+12+19+21+33。

⼆、算法描述仔细分析商⼈的⾛法,商⼈在每⼀格时,其实只有两种选择,要么向右⾛,要么向下⾛;他不可能向上⾛或者向左⾛,因为那只会离位于右下⾓的⽬的地越来越远,⽽且还⽩⽩花费更多的钱。

假设商⼈站在 [i][j] 格上,他只有两种可能的来路,要么从左边 [i][j-1] ⾛过来,要么从上⾯ [i-1][j] ⾛过来。

第⼀种情况,假设商⼈是从左边 [i] [j-1] ⾛过来的,那么他的上⼀步只能是:要么从左边的 [i][j-2] 格⼦过来,要么从上⾯的 [i-1][j-1] 格⼦过来。

第⼆种情况,假设假设商⼈是从上⾯ [i-1][j] ⾛过来的,那么他的上⼀步只能是:要么从左边的 [i-1][j-1] 格⼦过来,要么从 [i-2][j] 过来。

综上,我们可以总结出,商⼈站在任意⼀个格⼦时,只能有两种情况,从左边或者从上⾯来,⽽到底是从哪⾥来的,就取决于这两种来路哪个的累积价格更少。

所谓累积价格,就是从左上⾓的⼊⼝⾛到当前格⼦所花费的总费⽤。

运筹学实验总结

运筹学实验总结

运筹学实验总结引言:运筹学是一门综合了数学、经济学和工程学等多学科知识的学科,它通过建立数学模型和运用各种优化方法,帮助我们在现实问题中寻找最优解决方案。

在这学期的运筹学课程中,我们进行了一系列实验。

这些实验不仅加深了对运筹学理论的理解,还提供了一种应用运筹学方法解决问题的实践平台。

在本文中,我将总结我参与的运筹学实验,并分享我的体会和收获。

实验一:线性规划问题求解在这个实验中,我们学习了线性规划的基本概念和求解方法。

我选择了一个典型的生产调度问题作为实验题目。

通过建立数学模型,并运用线性规划软件,我成功地解决了这个问题。

通过这个实验,我深刻理解了线性规划问题的本质,以及如何利用线性规划方法找到最优解。

实验二:整数规划问题求解整数规划是线性规划的扩展,它在决策问题中更加实用。

在这个实验中,我选择了货物配送路线问题作为研究对象。

通过构建整数规划模型,并运用求解软件,我得到了最佳的货物配送方案。

这个实验不仅对我的数学建模能力提出了要求,还培养了我的实际问题解决能力。

实验三:动态规划动态规划是一种重要的优化方法,它广泛应用于最优化问题的求解。

在这个实验中,我们学习了动态规划的基本原理和设计思想。

我选择了旅行商问题作为研究对象,通过建立递推关系和寻找最优子结构,我成功地解决了该问题。

这个实验让我意识到了动态规划方法的强大威力,同时也对我的算法设计能力提出了更高的要求。

实验四:模拟退火算法模拟退火算法是一种全局搜索优化算法,具有很强的应用能力。

在这个实验中,我选择了旅行商问题作为研究对象,通过模拟退火算法的迭代和优化,我得到了一个较好的解。

通过这个实验,我掌握了模拟退火算法的基本原理和实现过程,也了解到了算法的优越性。

实验五:遗传算法遗传算法是一种模拟自然选择和遗传机制的优化算法。

在这个实验中,我选择了装箱问题作为研究对象。

通过运用遗传算法的交叉、变异和适应度选择,我得到了一个较好的装箱方案。

这个实验不仅对我的算法设计能力提出了更高的要求,还让我意识到了遗传算法的创新性和解决复杂问题的能力。

实验三动态规划

实验三动态规划

算法分析与设计实验报告学号姓名班级上课地点教师上课时间实验三动态规划1. 实验目的1.1理解动态规划算法的主要设计思想和基本步骤;1.2掌握用动态规划策略解决实际问题。

2. 实验环境2.1 Eclipse2.2 Window XP3. 实验内容3.1 矩阵连乘问题3.2 最长公共子序列问题3.3 0-1背包问题4. 教师批改意见成绩签字:日期:实验报告细表1.矩阵连乘问题1.1 算法设计思想(1) 分析最优解:计算A[i:j]的最优次序所包含的计算矩阵子链 A[i:k]和A[k+1:j]的次序也是最优的(2)建立递归关系:设计算A[i:j],1≤i≤j≤n,所需要的最少数乘次数m[i,j],则原问题的最优值为m[1,n] 当i=j 时,A[i:j]=Ai ,因此,m[i,i]=0,i=1,2,…,n 当i<j 时,j k i p p p j k m k i m j i m 1],1[],[],[-+++= 可以递归地定义m[i,j]为:⎪⎩⎪⎨⎧<+++==-<≤j i p p p j k m k i m j i j i m j k i }],1[],[{min 0],[1jk ik 的位置有j-i 种可能(3)计算最优值:用动态规划算法解此问题,可依据其递归式以自底向上的方式进行计算。

在计算过程中,保存已解决的子问题答案。

每个子问题只计算一次,而在后面需要时只要简单查一下,从而避免大量的重复计算,最终得到多项式时间的算法public static void MatrixChain(int []p,int [][]m,int [][]s) {int n=p.length-1;for(int i=1;i<=n;i++)m[i][i]=0; for(int r=2;r<=n;r++) for(int i=1;i<=n-r+1;i++) { int j=i+r-1; m[i][j]=m[i+1][j]+p[i+1][i][j]; s[i][j]=i; for(int k=i+1;k<j;k++) { int t=m[i][k]+m[k+1][j]+p[i-1][k][j]; if(t<m[i][j]){ m[i][j]=t; s[i][j]=k; } }}}(4)构造最优解:算法matrixChain 记录了构造最优解所需的全部信息。

动态规划实验报告

动态规划实验报告

实验课程:算法分析与设计实验名称:实验3 动态规划算法(综合性/设计性)实验目标:1、熟悉最长公共子序列问题的算法;2、初步掌握动态规划算法;实验任务:若给定序列X={x1,x2,…,xm},则另一序列Z={z1,z2,…,zk},是X的子序列是指存在一个严格递增下标序列{i1,i2,…,ik}使得对于所有j=1,2,…,k有:zj=xij。

例如,序列Z={B,C,D,B}是序列X={A,B,C,B,D,A,B}的子序列,相应的递增下标序列为{2,3,5,7}。

给定2个序列X和Y,当另一序列Z既是X的子序列又是Y的子序列时,称Z是序列X 和Y的公共子序列。

给定2个序列X={x1,x2,…,xm}和Y={y1,y2,…,yn},找出X和Y的最长公共子序列。

实验设备及环境:PC;C/C++的编程环境Visual C++。

实验主要步骤:(1)明确实验目标和具体任务;(2)理解实验所涉及的动态规划算法;(3)编写程序并实现动态规划算法;(4)设计实验数据并运行程序、记录运行的结果;实验数据及运行结果、实验结果分析及结论:(学生填写)#include <stdio.h>#include <string.h>void LcsLength(char *x,char *y,int m,int n,int c[][100],int b[][100]){puts(x);puts(y);int i,j;for(i=0;i<=m;i++)c[i][0]=0;for(j=1;i<=n;j++)c[0][j]=0;for(i=1;i<=m;i++)for(j=1;j<=n;j++) {if(x[i-1]==y[j-1]) {c[i][j]=c[i-1][j-1]+1;b[i][j]=0;}else if(c[i-1][j]>=c[i][j-1]) {c[i][j]=c[i-1][j];b[i][j]=1;}else {c[i][j]=c[i][j-1]; b[i][j]=-1;}}}void PrintLCS(int b[][100], char *x, int i, int j){ if(i==0 || j==0)return;if(b[i][j]==0) {PrintLCS(b,x,i-1,j-1);printf("%c",x[i-1]);}else if(b[i][j]==1)PrintLCS(b,x,i-1,j);elsePrintLCS(b,x,i,j-1);}void main(){char x[100]={"ABCBDAB"};char y[100]={"BDCABA"};int c[100][100];int b[100][100];int m,n;m=strlen(x);n=strlen(y);LcsLength(x,y,m,n,c,b); printf("最长子序列为:");PrintLCS(b,x,m,n); printf("\n");printf("最长子序列长度为:%d\n",c[m][n]);}实验结果:结果分析:在写规划方程时,只要对两条路径走到同一个点的情况稍微处理一下,减少可选的决策个数:从这个例子中可以总结出设计动态规划算法的一个技巧:状态转移一般。

《动态规划算法实验》实验报告

《动态规划算法实验》实验报告

实验3、《动态规划算法实验》一、实验目的1. 掌握动态规划方法贪心算法思想2. 掌握最优子结构原理3. 了解动态规划一般问题二、实验内容1. 编写一个简单的程序,解决0-1背包问题。

设N=5,C=10,w={2,2,6,5,4},v={6,3,5,4,6}2. 合唱队形安排问题【问题描述】N位同学站成一排,音乐老师要请其中的(N-K)位同学出列,使得剩下的K 位同学排成合唱队形。

合唱队形是指这样的一种队形:设K位同学从左到右依次编号为1,2…,K,他们的身高分别为T1,T2,…,TK,则他们的身高满足T1<...<Ti>Ti+1>…>TK(1<=i<=K)。

已知所有N位同学的身高,计算最少需要几位同学出列,可以使得剩下的同学排成合唱队形。

三、算法思想分析1.0-1背包采用动规算法主要是动规方程的思考,之后就是确定边界条件即可。

2.合唱队形问题应用了分治与动态规划的算法,先将所有队员依次做中间最高的同学,将问题分为左右来做,接下来只需要求得左边的最长上升子序列数、右边的最长下降子序列数即可。

四、实验过程分析1.0-1背包问题是背包问题的进一步条件限制,考虑清楚动规方程就不难,编程中对于m(i,j)的含义要清楚,搞混了就容易出错。

2.合唱队形问题的思想并不复杂,特别是如果已经掌握了最长上升子序列数的算法,在分别处理左右最长子序列时需要特别注意数组下标,一开始我用是i,j直接从0到左右的数据长度,但是一直出错,后来发现队员身高数组并不能完全用这些下标,特别是右边的函数,数组起始下标不是0,需要利用函数传递起始下标才能调用对应的数据段。

五、算法源代码及用户屏幕1.(1)算法源码/********************************0-1背包问题。

codeblocks C++2018.11.2********************************/#include <iostream>#include <iomanip>using namespace std;void knapSnack(int v[], int w[], int c, int n, int m[][11]);int main(){int v[] = {6, 3, 5, 4, 6};int w[] = {2, 2 ,6, 5, 4};int c = 10;int n = 5;int m[5][11];//初始化数组for(int i=0; i<5; i++){for(int j=0; j<11; j++){m[i][j] = 0;}}knapSnack(v, w, c, n, m);//输出结果cout<<setw(3)<<" ";for(int i=0; i<11; i++){cout<<setw(3)<<i;}cout<<endl;for(int i=0; i<5; i++){//输出行号cout<<setw(3)<<i+1;for(int j=0; j<11; j++){cout<<setw(3)<<m[i][j];}cout<<endl;}return 0;}void knapSnack(int v[], int w[], int c, int n, int m[][11]){ for(int i=0; i<n; i++){for(int j=0; j<11; j++){//边界条件if(i == 0){if(w[i] > j)m[i][j] = 0;elsem[i][j] = v[i];}/*动规方程j>w[i]m(i,j) = max{m(i-1,j), m(i-1,j-w[i])+v[i]}0<=j<w[i]m(i,j) = m(i-1,j)*/else{if(w[i] > j)m[i][j] = m[i-1][j];else{if(m[i-1][j] > (m[i-1][j-w[i]]+v[i]))m[i][j] = m[i-1][j];elsem[i][j] = m[i-1][j-w[i]]+v[i];}}}//控制列数的for循环}//控制行数的for循环}(2)用户屏幕2.(1)算法源码/***************************************************合唱队形问题codeblocks C++2018.11.2***************************************************/#include <iostream>#include <string.h>using namespace std;//计算左端合唱队人数int leftQueue(int a[], int _start, int _end);//计算右端合唱队人数int rightQueue(int a[], int _start2, int _end2);int main(){cout<<"Please enter total number:";int number;cin>>number;cout<<"Please input the height of each person (cm):"<<endl;int a[number]; //记录每个人身高//b数组分别记录当第n个人为合唱队中间人时,合唱队的总人数int b[number];int rightNumber[number]; //记录左端合唱队人数int leftNumber[number]; //记录右端合唱队人数for(int i=0; i<number; i++)b[i] = 0;for(int i=0; i<number; i++)cin>>a[i];int mostQueueNumber = b[0];for(int i=0; i<number; i++){//设置a[i]为最高的同学leftNumber[i] = leftQueue(a,0,i);rightNumber[i] = rightQueue(a,i,number-1);//计算合唱队总人数b[i] = leftNumber[i] + rightNumber[i] - 1;//计算合唱队最多的总人数if(mostQueueNumber < b[i])mostQueueNumber = b[i];}//计算最少出队人数int leastDequeueNumber = number - mostQueueNumber;cout<<"Minimum number of people out: "<<leastDequeueNumber<<endl;return 0;}int leftQueue(int a[], int _start, int _end){int leftMostNumber = 0;int n = _end-_start+1;//c数组记录i时的最长上升子序列数int c[n];int maxN;//初始化最长上升子序列数为1for(int i=0; i<n; i++){c[i] = 1;}for(int i=_start; i<_end+1; i++){maxN = 0;for(int j=i-1; j>=_start; j--){if(a[j]<a[i] && c[j]>maxN)maxN = c[j];c[i] = maxN + 1;}}leftMostNumber = c[n-1];return leftMostNumber;}int rightQueue(int a[], int _start2, int _end2){ int rightMostNumber = 0;int n2 = _end2-_start2+1;//c2数组记录i时的最长下降子序列数int c2[n2];int maxN2;//初始化最长下降子序列数为1for(int i=0; i<n2; i++){c2[i] = 1;}for(int i=_end2; i>=_start2; i--){maxN2 = 0;for(int j=i+1; j<=_end2; j++){if(a[j]<a[i] && c2[j-_start2]>maxN2)maxN2 = c2[j-_start2];c2[i-_start2] = maxN2 + 1;}}rightMostNumber = c2[0];return rightMostNumber; }(2)用户屏幕。

实验三 动态规划算法

实验三 动态规划算法

实验三动态规划算法一、实验目的进一步理解动态规划算法的基本思想,掌握设计有效算法的动态规划方法,会使用动态规划解决一些实际问题。

二、实验要求1、上机前的准备工作根据实验内容中所给题目,利用所学动态规划算法的基本设计思想设计算法并编写好上机程序,以提高上机效率;2、独立上机,输入、调试所编程序;3、上机结束后,写出实验报告。

4、上机时间:4学时三、实验内容算法实现题:1、3-3#include <iostream>using namespace std;const int N=4;int s[2*N]={0,3,4,2,1,3,4,2};//一共4堆石子,3,4,2,1int m[2*N][2*N];int h[2*N][2*N];int totalValue(int i,int j){int sum=0;for(int k=i;k<=j;k++)sum+=s[k];return sum;}void maxsum(int n) //求最大值{int i,j,r,k,t;for (i = 1; i <= n; i++) m[i][i] = 0;for ( r = 2; r <= n; r++)for ( i = 1; i <n - r+1; i++) {j=i+r-1;m[i][j] = m[i+1][j];h[i][j]=i;for ( k = i+1; k < j; k++) {t = m[i][k] + m[k+1][j];if (t> m[i][j]){m[i][j] = t;h[i][j]=k;}}m[i][j]+=totalValue(i,j);}}void minsum(int n)//求最小值{int i,j,r,k,t;for (i = 1; i <=n; i++) m[i][i] = 0; for ( r = 2; r <= n; r++)for ( i = 1; i < n - r+1; i++) { j=i+r-1;m[i][j] = m[i+1][j];h[i][j]=i;for ( k = i+1; k < j; k++) { t = m[i][k] + m[k+1][j];if (t<m[i][j]){m[i][j] = t;h[i][j]=k;}}m[i][j]+=totalValue(i,j);}}void Traceback(int i,int j,int h[][2*N]) {if(i==j)return;Traceback(i,h[i][j],h);Traceback(h[i][j]+1,j,h);cout<<i<<" "<<j<<endl;}void main(){int i,j,p,q,n=N;minsum(2*n);int min_result=m[1][n];p=1;q=n;for(i=2;i<=n;i++)if(min_result>m[i][n-1+i]){p=i;q=n-1+i;min_result=m[p][q];}cout<<"最小值:"<<min_result<<endl;Traceback(p,q,h);maxsum(2*n);int max_result=m[1][n];p=1;q=n;for(i=2;i<=n;i++)if(max_result <m[i][n-1+i]){p=i;q=n-1+i;max_result=m[p][q];}//cout<<p<<" "<<q<<endl;cout<<"最大值:"<<max_result<<endl;Traceback(p,q,h);}运行结果:2、3-4#include "iostream.h"void main( ){int a[50][50],data[50][50],b[50][50],i,j,n;cout<<"please input the number of rows:";//输入行数cin>>n;for( i=1;i<=n;i++)for(j=1;j<=i;j++){cin>>data[i][j];//将数据放到二维数组a[i][j]=data[i][j];b[i][j]=0;}for (i=n-1; i>=1;i--)for(j=1;j<=i;j++)if (a[i+1][j]>a[i+1][j+1]){a[i][j]=a[i][j]+a[i+1][j];b[i][j]=0;}else{a[i][j]=a[i][j]+a[i+1][j+1];b[i][j]=1;}cout<<"max="<<a[1][1]<<endl;j=1;for( i=1 ;i<=n-1;i++){cout<<data[i][j]<<"->";j=j+b[i][j];}cout<<data[n][j];}运行结果:3、3-6#include<iostream>using namespace std;const int N=4;intm[N+1][N+1]={{0,0,0,0,0},{0,0,5,8,20},{0,0,0,7,18},{0,0,0,0,2},{0,0,0 ,0,0}};int h[N+1][N+1];//由矩阵连乘的算法void Boat(int n){int i,j,r,k,t;for (i = 1; i <= n; i++) m[i][i] = 0;for ( r = 2; r <= n; r++)for ( i = 1; i <= n - r+1; i++) {j=i+r-1;h[i][j]=i;for ( k = i+1; k < j; k++) {t = m[i][k] + m[k][j] ;if (t < m[i][j]) { m[i][j] = t;h[i][j]=k;}}}}void Traceback(int i,int j,int h[][N+1]){if(i==j)return;Traceback(i,h[i][j],h);Traceback(h[i][j]+1,j,h);cout<<"A"<<i<<","<<h[i][j]<<"和"<<"A"<<h[i][j]+1<<","<<j<<endl;}void main(){int n=N;Boat(n);Traceback(1,n,h);cout<<m[1][N]<<endl;}运行结果:4、防卫导弹一种新型的防卫导弹可截击多个攻击导弹。

动态规划模型实验报告

动态规划模型实验报告

一、实验目的本次实验旨在通过动态规划模型的应用,深入理解动态规划的基本概念、解题步骤以及在实际问题中的应用。

通过实验,掌握动态规划模型的设计、求解和优化方法,提高解决复杂问题的能力。

二、实验内容1. 实验背景动态规划(Dynamic Programming,DP)是一种求解多阶段决策过程最优化的数学方法。

它适用于具有多阶段特性问题的求解,如背包问题、最长公共子序列问题、最短路径问题等。

动态规划的核心思想是将复杂问题分解为相互重叠的子问题,通过子问题的最优解构造原问题的最优解。

2. 实验步骤(1)选择实验题目本次实验选择背包问题作为实验题目。

背包问题是一个经典的动态规划问题,其目标是求在给定的物品重量和总重量限制下,如何选择物品使得背包内物品的总价值最大。

(2)建立动态规划模型根据背包问题的特点,我们可以将问题分解为以下子问题:- 子问题1:对于每个物品,选择放入背包或不放入背包。

- 子问题2:在物品已确定的情况下,计算当前背包的总价值。

状态表示:令dp[i][j]表示前i个物品放入容量为j的背包所能获得的最大价值。

状态转移方程:dp[i][j] = max(dp[i-1][j], dp[i-1][j-w[i]] + v[i]),其中w[i]表示第i个物品的重量,v[i]表示第i个物品的价值。

初始化:dp[0][j] = 0,表示不放入任何物品时的最大价值为0。

填表顺序:按照物品的顺序填表,从左到右,从上到下。

返回值:dp[n][m],其中n表示物品数量,m表示背包容量。

(3)编程实现使用Python编程语言实现背包问题的动态规划模型。

(4)实验结果与分析通过实验,我们可以得到以下结果:- 在给定的物品重量和总重量限制下,背包内物品的总价值最大为V。

- 在物品已确定的情况下,可以得到每个物品是否放入背包的决策。

(5)优化与改进- 使用滚动数组优化空间复杂度,减少存储空间。

- 优化状态转移方程,提高计算效率。

动态规划实验报告

动态规划实验报告

动态规划实验报告一、引言咱们今天说的可不是一般的编程技术,而是一个超级强大的工具——动态规划。

说白了,动态规划就像是给复杂问题找到了一条捷径,别看它名字听起来有点拗口,实际操作起来还是挺有意思的。

你有没有遇到过这样的问题:在一个复杂的游戏中,每走一步都要考虑前面的所有步骤,做一个不小心,就前功尽弃?这时候,动态规划就是你背后的那个“隐形助手”,帮你把问题拆开,简化成一个个小问题,然后一步步搞定。

简单说,动态规划就是把大问题分成小问题,然后小问题解决了,大问题自然也能解决。

这是不是有点像解题时,“分而治之”的思路呢?动态规划背后有一个超级简单的理念——最优子结构和重叠子问题。

是不是觉得很高大上?别担心,听我慢慢说给你听。

最优子结构就像是一个数学大叔告诉你:“先把问题分成一小块一小块,最后每一块都找最优解。

”至于重叠子问题,直白点说就是:别每次都重新做一遍相同的事情,重复计算只会让你浪费时间。

学会了这两点,你就能在编程的世界里游刃有余。

二、动态规划的核心思想1. 最优子结构:就拿经典的背包问题来说,背包里能装多少东西,关键看每次放入一个物品后的“最优选择”是什么。

要想知道最终背包里放什么,得先知道每一件物品能不能放进去,而每次选择是否放入某个物品,都可以看成是一个小问题。

所以说,动态规划的最优子结构就像是把大问题拆成了一个个“小战役”,每打赢一场,小战役累积起来,最终就能拿下大胜利。

2. 重叠子问题:你也许不太理解这是什么意思,其实就是“别让自己浪费时间做重复的事”。

比如你正在计算一串数字的和,每次加一个数字时,你都会回头从头开始重新加一次。

看似没啥问题,但实际上你会发现,这样的计算方式很低效,每次都从头算,能不浪费时间吗?当然不行。

所以动态规划的另一个重点就是用一个记忆表,把之前做过的计算结果存下来,下次再遇到相同的问题,就直接拿出来用,省时又省力。

3. 状态转移方程:想象一下,你在解一道问题,每次走一步都能看见前面已经走过的路。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

实验二动态规划
(一)、实验目的
通过编程实现动态规划的有关算法,理解动态规划的原理,掌握动态规划基本思想与应用技巧。

(二)、实验题目与要求:
实验题目1:最长公共子序列问题的算法
若给定序列X={x1,x2,…,xm},则另一序列Z={z1,z2,…,zk}是X的子序列是指存在一个严格递增下标序列{i1,i2,…,ik}使得对于所有j=1,2,…,k 有:zj=xij。

例如,序列Z={B,C,D,B}是序列X={A,B,C,B,D,A,B}的子序列,相应的递增下标序列为{2,3,5,7}。

给定2个序列X和Y,当另一序列Z既是X的子序列又是Y的子序列时,称Z是序列X 和Y的公共子序列。

给定2个序列X={x1,x2,…,xm}和Y={y1,y2,…,yn},找出X和Y的最长公共子序列。

实验要求:
1.理解动态规划算法的原理,认真阅读题目。

完善程序,实现该算法;
2.结果显示最长公共子序列。

实验提示:
先求最长公共子序列,X和Y的最长公共子序列的长度记录于c[m][n]中
public static int lcsLength(char [ ]x,char [ ]y,int [ ][ ]b)
{ int m=x.length-1;
int n=y.length-1;
int [][]c=new int [m+1][n+1];
for (int i = 1; i <= m; i++) c[i][0]=0;
for (int i = 1; i <= n; i++) c[0][i]=0;
for (int i = 1; i <= m; i++)
for (int j = 1; j <= n; j++) {
if (x[i]= =y[j]) { c[i][j]=c[i-1][j-1]+1; b[i][j]=1;}
else if (c[i-1][j]>=c[i][j-1]) { c[i][j]=c[i-1][j]; b[i][j]=2;}
else { c[i][j]=c[i][j-1]; b[i][j]=3;}
}
return c[m][n];
}
然后构造最长公共子序列
public static void lcs(int i,int j,char [] x,int [][] b)
{ if (i = =0 || j= =0) return;
if (b[i][j]= = 1){
lcs(i-1,j-1,x,b);
System.out.print(x[i]);
}
else if (b[i][j]= = 2) lcs(i-1,j,x,b); else lcs(i,j-1,x,b);
}
实验题目2:用两台处理机A和B处理n个作业。

设第i个作业交给机器A处理时需要时间ai,若由机器B来处理,有ai≥bi,而对于某些j,j≠i,有aj<bj。

既不能将一个作业分开由两台机器处理,也没有一台机器能同时处理2个作业。

设计一个动态规划算法,使得这两台机器处理完成这n个作业的时间最短(从任何一台机器开工到最后一台机器停工的总时间)。

实验要求:
1.理解动态规划算法的原理,认真阅读题目。

完善程序,实现该算法;
2.研究一个实例:
(a1, a2, a3, a4, a5, a6) = (2, 5, 7, 10, 5, 2) ;
(b1, b2, b3, b4, b5, b6)=(3, 8, 4, 11, 3, 4)。

结果显示处理完所有作业的最短时间。

实验题目3:计算矩阵连乘积
给定n个矩阵{A1,A2 ,...,An},其中Ai与Ai+1是可乘的,i=1,2,...,n-1。

考察这n个矩阵的连乘积A1A2...An,给出其最优计算次序,使矩阵连乘运算乘法次数最少。

实验要求:
1.理解动态规划算法的原理,认真阅读题目。

完善程序,实现该算法;
2.给定五个矩阵:A1:5*10;A2:10*4;A3:4*6;A4:6*10;A5:10*2,给出最优计算次序和乘法次数。

实验提示:
设计算A[i:j],1≤i≤j≤n,所需要的最少数乘次数m[i,j],则原问题的
[][][]{}
⎪⎩⎪⎨⎧<+++==-<≤j i p p p j k m k i m j i j i m j k i j k i 1,1,min 0,最优值为m[1,n]。

递归定义m [i ,j ]为:
public static void matrixChain(int [] p, int [][] m, int [][] s)
{ int n=p.length-1;
for (int i = 1; i <= n; i++) m[i][i] = 0;
for (int r = 2; r <= n; r++)
for (int i = 1; i <= n - r+1; i++) {
int j=i+r-1;
m[i][j] = m[i+1][j]+ p[i-1]*p[i]*p[j];
s[i][j] = i;
for (int k = i+1; k < j; k++) {
int t = m[i][k] + m[k+1][j] + p[i-1]*p[k]*p[j];
if (t < m[i][j]) { m[i][j] = t; s[i][j] = k; }
}
}
}
实验题目4:0-1背包问题
给定n 种物品和一背包。

物品i 的重量是wi ,其价值为vi ,背包的容量为C 。

问应如何选择装入背包的物品,使得装入背包中物品的总价值最大? 实验要求:
1. 理解动态规划算法的原理,认真阅读题目。

完善程序,实现
该算法;
2. 自行设计输入数据和输出格式。

实验提示:
设n 个物品的重量存储在数组w[n]中,价值存储在数组v[n]中,背包容量为C ,数组V[n+1][C+1]存放迭代结果,其中V[i][j]表示前i 个物品装入容量为j 的背包中获得的最大价值,数组x[n]存储装入背包的物品,动态规划法求解0/1背包问题的算法如下:
public static int KnapSack(int C, int w[ ], int v[ ],int[][]V)
{ int n=v.length;
for (int i=0; i<=n; i++) V[i][0]=0; //初始化第0列
for (int j=0; j<=C; j++) V[0][j]=0; //初始化第0行
for (int i=1; i<=n; i++) //计算第i行,进行第i次迭代
for (int j=1; j<=C; j++)
if (j<w[i]) V[i][j]=V[i-1][j];
else V[i][j]=Math.max(V[i-1][j], V[i-1][j-w[i]]+v[i]);
j=C; //求装入背包的物品
for (int i=n; i>0; i--)
{
if (V[i][j]>V[i-1][j]) { x[i]=1; j-=w[i]; }
else x[i]=0;
}
return V[n][C]; //返回背包取得的最大价值
(三)、实验步骤
1.对于以上题目要认真分析和理解题意,任选两个题目设计出
算法;
2.详细写出正确的高级语言源程序;
3.上机录入并调试程序;
4.请指导教师审查程序和运行结果并评定成绩;
5.撰写并上交实验报告。

(四)、实验报告内容
1.班级、学号、姓名、实验日期;
2.实验题目;
3.对于实验题目的理解与说明;
4.程序功能与框架;
5.设计说明(存储结构、特别构思等);
6.调试报告(调试过程中遇到的问题及如何解决此问题,程序
设计的得失,对于改进程序的设想、经验、体会等);
7.对算法的时间复杂性进行分析;
8.附录:源程序清单(加必要的注释)、测试数据及运行结果。

(五)、实验成绩考核方法
实验成绩由实验结果、问题回答以及实验报告综合评定。

相关文档
最新文档