矩陣連乘問題

2021-08-30 06:43:23 字數 1668 閱讀 1271

問題描述:

矩陣連乘問題是通過給矩陣連乘時加括號,使得總的計算量最小。

考慮3個矩陣相乘的例子, a1,a2,a3,假設這3個矩陣的維數分別為 10x100,100x50,5x50

若按照((a1a2)a3)方式計算,需要的數乘次數為10x100x5+10x5x50 = 7500

若按照(a1(a2a3))方式計算,需要的數乘次數為100x5x50+10x100x50 =75000

問題分析:

1.分析最優解的結構 

設計求解具體問題的動態規劃演算法的第一步是刻畫該問題的最優解的結構特徵。我們將矩陣連乘積aiai+1....aj簡記為a[ i : j ]。考察計算a[ 1: n]的最優計算次序。設這個計算次序在矩陣ak和ak+1之間將矩陣鏈斷開,1<=k2.建立遞迴關係

設計動態規劃演算法的第二步就是遞迴地定義最優值。對於矩陣連乘積的最有計算次序問題,設計算a[i:j], 1<=i<=j<=n,所需的最少數乘次數為m[i][j],則原問題的最優值為m[1][n]。

當i=j時,a[i;j ]=ai,為單一矩陣,無需計算,因此m[i][i]=0。

當i < j時,可以利用最優子結構的性質來計算m[i][j]。事實上,若計算a[i:j]的最優次序在ak和ak+1之間斷開,i<=k當i=j   m[i][j] = 0

當im[i][j]給出了最優值,即計算a[i:j]所需的最少數乘次數。同時還確定了計算a[i:j]的最優次序中的斷開位置k,也就是說,對於這個k有

m[i][j]=m[i[k]+m[k+1][j] + pi-1*pk*pj

若將對應於m[i][j]的斷開位置k記為s[i][j],在計算最優值m[i][j]後,可以遞迴地有s[i][j]構造出相應的最優解。

3. 計算最優值

根據計算m[ i ][ j ]的遞迴式,容易寫乙個遞迴演算法計算m[ 1 ][ n ]。但是簡單地遞迴將好費指數計算時間。在遞迴計算時,許多子問題被重複計算多次。這也是該問題可以用動態規劃演算法求解的又一顯著特徵。

用動態規劃演算法解決此問題,可依據其遞迴是以自底向上的方式進行計算。在計算的過程中,儲存以解決的子問題答案。每個子問題只計算一次,而在後面需要時只要簡單查一下,從而避免大量的重複計算。

4. **實現

下面的演算法中,輸入引數p0,p1,……p2儲存在陣列p中。演算法除了輸出最優值陣列外還輸出記錄最優斷開置的陣列s.

演算法首先計算出m[i][i] = 0,i=1,2,3……,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].

#includeusing namespace std;

const int maxn=1e3+5;

int num[maxn][maxn],by[maxn][maxn];

int p[maxn];

void solve1(int n)//動態規劃

return num[l][r];

}void display(int l,int r)

{ if(r==l)

{ cout<

其中兩種解答分別為動態規劃寫法和備忘錄寫法,都是通過記錄來減少計算,區別是動態規劃直下向上,備忘錄寫法自頂向下。

矩陣連乘問題

矩陣連乘問題 應用動態規劃演算法,將前面計算的重複值儲存,一次來推進下一步的計算,直到得到m 1 n 的值,為最少的乘法次數 m i j 表示計算a i.j 所需的最少數乘次數 m i j min i s i j 記錄斷開位置,也就是最少計算次數的中間位置。include using namespa...

矩陣連乘問題

由於矩陣的乘法滿足結合律,故計算矩陣的連乘積可以有許多不同的計算次序。這中計算次序 可以用加括號的方式來確定。例如,矩陣連乘積a1a2a3a4可以有5種不同的完全加括號方式 a1 a2 a3a4 a1 a2a3 a4 a1a2 a3a4 a1 a2a3 a4 a1a2 a3 a4 矩陣a和b可乘的條...

矩陣連乘問題

矩陣連乘問題 問題分析 最優子結構性質假設n個矩陣連乘的最優加括號方案為 a1.ak ak 1.an 注 此處省略了a1.ak,ak 1.an兩個子矩陣內部的括號 則加括號方案 a1.ak 是子矩陣鏈a1.ak的最優加括號方案,ak 1.an 是ak 1.an的最優加括號方案。證明略。但可證明該假設...