实验报告
课程名称 《算法分析与设计》 实验日期 2021 年 5 月 3 日
学生姓名 郑超逸 所在班级 计科195 学号 2019211909055
实验名称 矩阵链的乘法
实验地点 实验室 同组人员
1.问题
设A1,A2,……,An为 n 个矩阵的序列,其中 为 阶矩阵,这个矩阵链的输入用向量P=<P0,P1,….,Pn>给出。
给定向量P,确定一种乘法次序,使得基本运算的总次数达到最小。
2.解析
例如, P=<10,100,5,50>,则A1:10×100,A2:100×5,A3:5×50
(A1A2)A3:10×100×5+10×5×50 = 7500
A1(A2A3):10×100×50+100×5×50 = 75000
这个×看作一种符号表示多少行多少列的矩阵
P中有四个向量表示三个矩阵形成了一个矩阵链
(A1A2)A3,计算次数:
首先A1与A2相乘,形成一个10×5的矩阵,其中每一个数的计算次数都为100次,即:10×5×100
然后A1与A2相乘得到的矩阵与A3相乘,同理10×5与5×50相乘,即:10×50×5
将上述条件相加,得到基本运算总次数,即:一次矩阵相乘就+一次运算次数
上述例子中,因为结合律导致了运算次数有了巨大的差异。
一种思路是使用蛮力算法:
枚举所有可能的乘法次序,针对每种次序计算基本运算的次数,从中找出具有最小运算次数的乘法次序,每一种乘法次序对应了一种在 n 个项中加 n-1 对括号。
例如:上述式子中3个项有2对括号
核心思想是翻转:但证明过程没看懂,我就不分析了,给出结论
n对括号的匹配数:
,然后查看它的复杂度:W(n)=Ω( )=Ω( )
阶乘函数>多项式>对数
所以基本不可能使用蛮力算法求解
另外一种就是使用动态规划的方法求解:
Ai… j:表示矩阵链相乘的子问题Ai Ai+1…Aj;
m[i… j]:表示得到乘积Ai… j所用的最少基本运算次数;
假定,最后一次相乘发生在矩阵链Ai…k和Ak +1… j之间,即
Ai…k Ak +1… j Ai Ai+1…Aj =(Ai Ai+1…Ak )(Ak +1 Ak +2 …Aj ) k =i,i +1,…, j -1
那么就会有很多可能性,如下所示:
e.g.:Ai (Ai+1…Aj ) (Ai Ai+1 )(Ai+2 …Aj ) (Ai Ai+1 Ai+2 …)(Aj-1 Aj ) (Ai Ai+1 Ai+2 …Aj-1 )Aj
表示为:
其中 Ai =Pi-1×Pi Ak =Pk-1×Pk Aj =Pj-1×Pj
min表示为其中三项每项的计算次数是最小的,
命题 m[i…j]=min{m[i,k]+m[k+1,j]+Pi-1PkPj} i≤k<j满足优化原则,即m[i…j]最小值时,m[i,k]和m[k+1,j]也是最小的。
反证法:假设m[i,k]不是最小的,存在更小的m’[i,k]<m[i,k],则
m’[i…j]=min{ m’[i…k]+m[k+1,j]+Pi-1PkPj}<m[i…j]=min{m[i,k]+m[k+1,j]+ Pi-1PkPj }是成立的,那么存在更小的m’[i…j]与已知的m[i…j]最小矛盾
所以min表示为其中三项每项的计算次数是最小的
3.设计
//令所有m[i,j]初值为0,s[i,j]的初值为i,1≤i≤j≤n
For r=2 to n do //r 为当前问题规模(长度)
For i=1 to n-r+1 do //i 的起点不断变化,各种 r 长
j=i+r-1 //不同终点
m[i, j] =m[i +1, j]+Pi-1 Pk Pj //划分为 Ai (Ai+1…Aj )
s[i, j] =i
For k=i+1 to j-1 do //不同的划分位置
t =m[i,k]+m[k+1, j]+Pi-1 Pk Pj
If t<m[i,j]
Then m[i,j]=t
s[i,j]=k
4.分析
O(n^3)
5.源码
https://github.com/Lin02993/Algorithm-Analysis-and-Practice-on-the-job