矩阵连乘问题算法分析与设计.docx
- 文档编号:25807145
- 上传时间:2023-06-15
- 格式:DOCX
- 页数:23
- 大小:72.11KB
矩阵连乘问题算法分析与设计.docx
《矩阵连乘问题算法分析与设计.docx》由会员分享,可在线阅读,更多相关《矩阵连乘问题算法分析与设计.docx(23页珍藏版)》请在冰豆网上搜索。
矩阵连乘问题算法分析与设计
矩阵连乘问题《算法分析与设计》
设计性实验报告
课程名称:
《算法分析与设计》矩阵连乘问题实验题目:
长:
组员一:
成
二:
成员成员三:
数学与计算机科学系别:
系
专业班级:
指导教师:
实验日期:
一、实验目的和要求
实验目的
熟悉动态规划算法设计思想和设计步骤,掌握基
本的程序设计方法,培养学生用计算机解决实际问题的能力。
实验要求
1、根据实验内容,认真编写源程序代码、上机调试程序,书写实验报告。
2、本实验项目考察学生对教材中核心知识的掌握程度和解决实际问题的能力。
3、实验项目可以采用集中与分散实验相结合的方式进行,学生利用平时实验课时间和课外时间进行实验,要求在学期末形成完整的项目程序设计报告。
二、实验内容提要
矩阵连乘问题给定n个矩阵{A,A,…,A},其中,Ai与Ai+1是可乘的,n21A,A,…,A。
由于矩阵乘法满足结n-1。
考查这n个矩阵的连乘积i=1,2,…,n12合律,故计算矩阵的连乘积可以有许多不同的计算次序。
这种计算次序可以用加括号的方式来确定。
若一个矩阵连乘积的计算次序完全确定,也就是说该连乘积已完全加括号,则可以依此次序反复调用2个矩阵相乘的标准算法计算出矩阵连乘积。
完全加括号的矩阵连乘积可递归地定义为:
(1)单个矩阵是完全加括号的;
(2)矩阵连乘积A是完全加括号的,则A可表示为2个完全加括号的矩阵连乘积B和C的乘积并加括号,即A=(BC)。
三、实验步骤下面考虑矩阵连乘积的最优计算次序问题的动态规划方法。
(1)分析最优解的结构(最优子结构性质)设计求解具体问题的动态规划算法的第一步是刻画该问题的最优解结构特征。
对于矩阵乘积的最优计算次序问题也不例外。
首先,为方便起见,降-1-
矩阵乘积AiAi+1…Aj简记为A[i:
j]。
考查计算A[1:
n]的最优计算次序。
设这个计算次序在矩阵Ak和Ak+1之间将矩阵链断开,1<=k k]和A[k+1: n],然后将计算结果相乘得到A[1: n]。 依此计算次序,总计算量 为A[1: k]的计算量加上A[k+1: n]的计算量,再加上A[1: k]和A[k+1: n]相乘的计算量。 这个问题的一个关键特征是: 计算A[1: n]的最优次序所包含的计算矩阵子链A[1: k]和A[k+1: n]的次序也是最优的。 事实上,若有一个计算A[1: k]的次序需要的计算量更少,则用此次序替换原来计算A[1: k]的次序,得到的计算A[1: n]的计算量将比按最优次序计算所需计算量更少,这是一个矛盾。 同理可知,计算A[1: n]的最优次序所包含的计算矩阵子链A[k+1: n]的次序也是最优的。 因此,矩阵连乘积计算次序问题的最优解包含着其子问题的最优解。 这种性质称为最优子结构性质。 问题的最优子结构性质是该问题可用动态规划算法求解的显著特征。 (2)建立递归关系对于矩阵连乘积的最优计算次序问题,设计算A[i: j],1= 当i=j时,A[i: j]=Ai为单一矩阵,无需计算,因此,m[i][i]=0,i=1,2,......,n。 当i 事实上,若计算A[i: j]的最优次序在Ak和Ak+1之间断开,i= 由于在计算时并不知道断开点k的位置,所以k还未定。 不过k的位置只有j-i种可能,即k属于{i,i+1,......,j-1}。 因此,k是这j-i个位置中使计算量达到最小的那个位置。 从而m[i][j]可以递归地定义为当i=j,m[i][j]=0;当i -2- m[i][j]给出了最优值,即计算A[i: j]所需的最少数乘次数。 同时还确定了计算A[i: j]的最优次序中的断开位置k,也就是说,对于这个k有m[i][j]=m[i][k]+m[k+1][j]+p[i-1]*p[k]*p[j] 若将对应于m[i][j]的断开位置k记为s[i][j],在计算出最优值m[i][j]后,可递归地有s[i][j]构造出相 应的最优解。 (3)计算最优值根据计算m[i][j]的递归式,容易写一个递归算法计算m[i][n]。 .稍后将看到,简单的递归计算将耗费指数计算时间。 注意到在递归计算过程中,不同的子问题个数只有θ(n^2)个。 事实上,对于1<=i<=j<=n不同的有序对(i,j)对应于不同的子问题。 因此,不同的子问题的个数最多只有n*(n-1)/2+n=θ(n^2)个。 由此可见,在递归计算时,许多子问题被重复计算多次。 这也是该问题可以动态规划算法求解的又一显著特征。 用动态规划算法解此问题,可依据其递归式以自底向上的方式进行计算。 在计算过程中,保存已解决的子问题答案。 每个子问题只计算一次,而在后面计算时只需简单查一下,从而避免大量重复计算,最终得到多项式时间的算法。 下面给出的动态规划算法matrixChain中,输入参数{p0,p1,p2....,pn}存储于数组p中。 算法除了输出最优值数组m外还输出记录最优断开位置的数组s。 算法matrixChain,首先计算出m[i][i]=0,i=1,2,....,n。 然后,根据递归式,按矩阵链长递增的方式依次计算m[i][i+1],i=1,2,.....,n-1,(矩阵链长度为2);m[i][i+2],i=1,2,.....n-2,(矩阵链长为3);......。 在计算m[i][j]时,只用到已计算出的m[i][k]和m[k+1][j]。 (4)构造最优解动态规划算法的第四步屎构造问题的最优解。 算法matrixChain只是计算出了最优值,并未给出最优解。 也就是说,通过算法matrixChain的计算,只知道最少数乘次数,还不知道具体应按什么次序做矩阵乘法才能达到最少的数乘次数。 -3- 事实上,算法matrixChain已记录了构造最优解所需要的全部信息。 S[i][j]中的数k表明计算矩阵链A[i: j]的最佳方式应在矩阵Ak和Ak+1之间断开,即最优的加括号方式应为(A[i: k])(A[k+1: j])。 因此,从是[1][n]记录的信息可知计算A[1: n]的最优加括号方式为(A[1: s[1][n]])(A[s[1][n]+1: n]).而 A[1: s[1][n]]的最优加括号方式为(A[1: s[1][s[1][n]]])(A[s[1][s[1][n]]+1: s[1][s[1][n]]]).同理可知确定A[s[1][n]+1: n]的最优加括号方式为是s[s1][n]+1][n]出断开,······,照此递推下去,最终可以确定A[1: n]的最优完全加括号方式,即构造出问题的一个最优解。 下面的算法traceback按算法matrixChain计算出的断点矩阵s指示的加括号方式输出计算A[i: j]的最优计算次序。 voidtraceback(inti,intj,ints[][N+1])//用递归来实现输出得到最小数乘次数的表达式 { if(i==j) { printf(A%d,i); } else { printf((); traceback(i,s[i][j],s); traceback(s[i][j]+1,j,s); printf()); -4- } } 要输出A[1: n]的最优计算次序只要调用上面的traceback(1,n,s)即可。 对于上面所举得例子,通 过调用算法traceback(1,6,s),可输出最优计算次序((A1(A2A3))((A4A5)A6))。 四、实验实施的条件 计算机机房,微型计算机,VisualC++6.0软件或C#。 五、程序代码 下面是算法的完整程序代码。 版本: c语言版本;开发人员: 王东亮、唐浩、陶胜、赵强 #include #defineN100//定义最大连乘的矩阵个数为100个 voidmatrixChain(intp[],intm[N+1][N+1],int s[N+1][N+1])/*用m[i][j]二维数组来存储Ai*......Aj的最小数乘次数,用s[i][j]来存储使Ai......Aj获得最小数乘次数对应的断开位置k,需要注意的是此处的N+1非常关键,虽然只用到的行列下标只从1到N但是下标0对应的元素默认也属于该数组,所以数组的长度就应该为N+1*/ -5- { intn=N;//定义m,s数组的都是n*n的,不用行列下标为0的元素,但包括在该数组中 for(inti=1;i<=n;i++) m[i][i]=0;/*将矩阵m的对角线位置上元素全部置0,此时应是r=1的情况,表示先计算第一层对角线上个元素的值*/ for(intr=2;r<=n;r++)//r表示斜对角线的层数,从2取到n { for(inti=1;i<=n-r+1;i++)//i表示计算第r层斜对角线上第i行元素的值 { intj=i+r-1;//j表示当斜对角线层数为r,行下标为i时的列下标 m[i][j]=m[i+1][j]+p[i-1]*p[i]*p[j];//计算当断开位置为i时对应的数乘次数 s[i][j]=i;//断开位置为i for(intk=i+1;k { -6- int t=m[i][k]+m[k+1][j]+p[i-1]*p[k]*p[j];/*计算当断开位置k为从i到j(不包括i和j)的所有取值对应 的(Ai*......*Ak)*(Ak+1*.......Aj)的数乘次数*/ if(t { m[i][j]=t;//将Ai*......Aj的最小数乘次数存入m[i][j] s[i][j]=k;//将对应的断开位置k存入s[i][j] } } } } } voidtraceback(inti,intj,ints[][N+1])//用递归来实现输出得到最小数乘次数的表达式 { if(i==j) { printf(A%d,i); -7- } else { printf((); traceback(i,s[i][j],s); traceback(s[i][j]+1,j,s); printf()); } } voidmain() { intn;//用来存储矩阵的个数 intq[2*N];/*用q数组来存储最原始的输入(各矩阵的行和列),主要目的是为了检验这N个矩阵是否满足连乘的条件*/ intp[N+1],flag=1;/*用p[i-1],p[i]数组来存储A的阶数,flag用来判断这N个矩阵是否满足连乘*/ intm[N+1][N+1];//用m[i][j]二维数组来存储Ai*......Aj的最小数乘次数 ints[N+1][N+1];//用s[i][j]来存储使Ai......Aj获得最小数乘次数对应的断开位置k -8- 牰湩晴? 请输入矩阵的个数(小于100): ); scanf(%d,&n); for(inti=0;i<=2*n-1;i++)//各矩阵的阶数的输 入先存入数组q中接受检验 { if(i%2==0) { printf(********************\n); printf(*请输入A%d的行: (i/2)+1); } else { 牰湩晴? 列************: ); } scanf(%d,&q[i]); } for(i=1;i<=2*n-2;i++)//矩阵连乘条件的检验 { if(i%2! =0&&q[i]! =q[i+1]) { flag=0; break; -9- } } for(intj=1;j<=n-1;j++) { p[j]=q[2*j]; } if(flag! =0) { p[0]=q[0]; p[n]=q[2*n-1]; matrixChain(p,m,s); p楲瑮? 尨式子如下: \n); traceback(1,n,s); printf(\ ); 牰湩晴? 最小数乘次数为%d\n,m[1][n]); } else { 牰湩晴? 这%d个矩阵不能连乘! \n,n); } } 实验结果: -10- 一、输入正确的情况: 二、输入有误的情况: -11- 六、编程体会 经过了几天的连续研究,终于小有收获,也 渐渐理解了动态规划的基本思想,动态规划算法与分治法类似,其基本思想也是将待解问题分解成若干个子问题,先求解子问题,,然后从这些子问题的解得到原问题的解。 与分治法不同的是,适合于用动态规划法求解的问题,经分解得到的子问题往往不是相互独立的。 若用分治法解这类问题,则分解得到的子问题数目太多,以至于最后解决原问题需要耗费指数时间。 然而,不同子问题的数目常常只有多项式量级。 在分治法求解时,有些子问题被重复计算了多次。 如果能够保存已解决的子问题的答案,而在需要时再找出已求得的答案,就可以避免大量重复计算,从而得到多项式时间算法。 为了达到这个目的,可以用一个表来记录所有已解决的子问题的答案,不管该子问题以后是否被用到,只要它被计算过,就将其结果填入表中。 这就是动态规划的基本思想。 具体的动态规划算法是多种多样的,但它们具有相同的填表格式。 -12- 动态规划算法适用于解最优化问题。 通常可以按以下步骤设计动态规划算法: (1)找出最优解的性质,并刻画其结构特征; (2)递归地定义最优值; (3)以自底向上的方式计算出最优值; (4)根据计算最优值时得到的信息,构造最优解。 虽然已经了解了动态规划算法的基本思想,而且也参考了书上的算法,但是实际的情况却并不是那么顺利,我按照书上编写程序之后,发现有很多逻辑错误,应该是编写环境不同,所以出现了一系列的问题,最后经过自己的多番研究发现了许多c语言有许多默认的规则: 就拿数组来讲,在计算数组m和数组s时,虽然我们不用到下标为零的元素,所以我一开始定义用长度为N*N的m数组和s数组来分别存储矩阵的最小数乘次数和其对应的断开位置,但经过多次调试之后,发现总是在求m[*][N]和s[*][N]时就会出错,后来才知道c语言的默认规则: 不管我们用不用数组的零下标元素,下标为零-13- 数s的元素都默认在该数组中,因此,必须把m和组的行列长度都必须加一才行,经过这次程序设计之后,我懂得了一个道理,做程 序设计,不仅要弄透解决这个问题的基本思想和算法,而且要注意编程过程中的一些细节性问题,例如一些特定编程环境的默认规则,而且还要要求我的逻辑思路一定要清晰,不然的话,很难发现自己先前所犯下的逻辑错误,这样就很容易造成事倍功半,效率低下。 以上就是我这次的程序设计编程体会。 七、成绩评定根据学习态度,任务完成质量(应用程序的难易程度、界面的友好性、程序的正确程度)和实报告质量进行打分,满10分 学习任务实验报成质质合 姓名、学号(25%)(50%)(25%) 组长: 成员一: 成员二: 成员三: -14- -15-
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 矩阵 问题 算法 分析 设计