題目:n個矩陣連乘,求最少的乘法運算次數以及結合方式
假設矩陣a為r1*r2,矩陣b為r2*r3,所以m=a*b=r1*r2*r3。當有多個矩陣相乘的時候,矩陣以不同的方式結合的時候其運算次數是不同的。
例如:m=m1 * m2 * m3 * m4
[5*20] [20*50] [50*1] [1*100]
((m1*m2)*m3)*m4=5000+250+500=5750
而m1*(m2*(m3*m4))=5000+100000+10000=115000
如果按照(m1*(m2*m3)*m4)=1000+100+500=1600
上面的例子說明根據不同的結合順序,運算的次數是不同的。現在我們就是要求通過哪種順序所進行的乘法運算次數最少,並且求出運算最少的次數是多少。
演算法思想:
記mi*mi+1*mi+2*...*mj為mij,矩陣的大小為:m1為r1*r2,m2為r2*r3,m3為r3*r3,m4為r4*r5。r1,r2,r3,r4,r5分別為5,20,50,1,100.
(1)首先計算矩陣相乘個數為2的3種情況。
m12=m1*m2=r1*r2*r3=5000,m23=r2*rr*r4,m34=r3*r4*r5=1000,m34=5000
(2)計算相乘矩陣個數為3的2種情況
m13=m1*m2*m3,目標是求出m13的乘法運算次數最小值。m13=min=min=m12*m3+r1*r3*r4=1100
同理 m24=m2*m3*m4=min=min=3000;
(3)最後計算相乘矩陣個數為4的最終結果:
m14=min(m13*m4+r1*r4*r5,m12*m34+r1*r3*r4,m1*m24+r1*r2*r5)==1600
演算法如下
#include using namespace std;int r[100],com[100][100];
int course(int i,int j)
else
{u=course(i,i)+course(i+1,j)+r[i]*r[i+1]*r[j+1];
com[i][j]=i;
for(int k=i;k
遞迴呼叫的過程如下:
1-2,2-3,3-4等子問題都被遞迴呼叫了2次,子問題存在重複。可以採用備忘錄方法解決該問題,設定乙個全域性變數m[i][j[,儲存已經計算過的course(i,j)的值,下次呼叫的時候直接使用。
非遞迴演算法
非遞迴的演算法計算過程和演算法主要思想裡面的一致。運算的矩陣的個數從少到多慢慢增加。
for(int i=1;i
動態規劃之矩陣鏈相乘
在看這張之前,最好看看我寫的 動態規劃詳解 裡面都是講理論基礎,我下面的分析都是在此基礎上進展的。問題描述 詳見演算法導論p197 p198 已知 給定n個矩陣構成的乙個矩陣鏈 a1,a2,an 矩陣ai的維數為pi 1 pi 求 決定該矩陣鏈的乘法結合順序 即加括號 使得矩陣鏈乘法的執行時間最短 ...
動態規劃 矩陣鏈相乘
實驗題目3 矩陣鏈乘法 11.1日實驗 要求 1 設計暴力法,產生所有矩陣鏈相乘以組合情況,寫出 並除錯成功 2 設計動態規劃演算法,寫出 尋找最小乘法次數和對應相乘的順序,並除錯成功 3 隨機產生由10個矩陣,測試 2 的 輸出最小乘法次數和相乘的順序。from random import def...
動態規劃 矩陣鏈相乘
設s1,a2,a3,an為n個矩陣的序列,其中ai為pi 1 pi階矩陣,這個矩陣鏈的輸入用向量p 給出。給定向量p,確定一種乘法次序,使得基本運算的總次數達到最小。我才用的矩陣為 a1 30 35 a2 35 15 a3 15 5 a4 5 10 a5 10 20 a6 20 25 那麼得到的p ...