計算機演算法:Strassen矩陣乘法

木子木發表於2012-12-12

簡介

Strassen矩陣乘法是典型的分而治之演算法。我們已經見過諸如歸併排序,Karatsuba大數乘法的分而治之的演算法。讓我們再次領略一下分而治之的含義。

與動態程式設計的“分散”得到子解決方案是為了得到最終的解決方案不同。在這裡,我們更多的是談論如何把子方案拼接起來。一般問題的子問題的解決方案是平等的,以某種方式定義它們的合併。

歸併排序演算法就是一個典型的例子。歸併排序中,有兩個有序表,想要把合併為一個有序表。當然,歸併排序中最棘手的問題就是合併本身。通過2個有序表A和B,把A,B中的每個子序列合併。說的有點偏離話題了,但是這就是歸併排序的弱點,儘管歸併排序最壞的時間複雜度是O(n,log(n)),快速排序通常是首選,因為它沒有合併。快速排序只是連線兩個子陣列。注意,在快序排序中子序列的長度是一般情況下是不同的。儘管它的最壞的時間複雜度是O(n ^ 2),通常優於歸併排序。

上面這個簡單的例子向我們說明了,有時候合併兩個子問題的解決方案實際上並不是一項簡單的任務。因此在使用任何分而治之方法時,必須小心。

歷史

施特拉森,出生於1936年,德國數學家。他有關概率的作品很知名,但是在電腦科學和演算法領域中也很知名,因為他的矩陣演算法。他的矩陣演算法仍然是優於一般矩陣乘法演算法主要方法。

1969,拉森第一次公開了這個演算法並證明了n ^ 3演算法並不是最優的。實際上拉森給出的解決方案只是稍微好一些。但他的貢獻是巨大的,因為這引發了更多的關於矩陣乘法的研究,產生了更快的方法,即Coppersmith-Winograd演算法,時間複雜度為O(n ^ 2,3737)。

綜述

通常情況下,兩個矩陣A[NxN]和B[NxN]相乘的演算法是相當簡單的。儘管這要比兩個數相乘難一些,儘管它是不可交換的,但仍然非常簡單,,只是算起來緩慢。

我們先來定義一個矩陣 A[NxN]。 當我們談及NxN的矩陣時,通常認為是一個N行乘N列的正方形網格。在每一個A[i][j]中填入值。

enter image description here

當然,作為開發者,我們可以把矩陣作為二維陣列。

// PHP two-dimensional array
$a = array(
    0 => array($v1, $v2, $v3, $v4),
    1 => array($v5, $v6, $v7, $v8),
    2 => array($v9, $v10, $v11, $v12),
);

不要忘記NxN矩陣僅是一個矩陣的例子。同樣我們可以建立其他任何大小的矩陣NxM(N < > M)。

然而矩陣相乘中,矩陣的大小是至關重要。為什麼呢?

正如我上面所說的矩陣相乘與數字相乘不同。首先,矩陣乘法中兩個矩陣是不能交換的。

enter image description here

其次,是矩陣A乘矩陣B的方式

enter image description here

這僅適用於 NxN的矩陣,看一下矩形矩陣相乘的問題。事實上,這是不可能發生,除非矩陣A的第二維度不相等矩陣B的第一個維度。

enter image description here

希望我們現在談的是平方矩陣都有完全相同的維度。

我們已經知道兩個平方矩陣(具有相同維度NxN)如何相乘了,現在讓我們評估時間複雜度的通用演算法。

僅當如下情況,AB = C:

C[i][j] = sum(A[i][k] * B[k][j]) for k = 0 .. n

有n ^ 3的操作。讓我們試著找出一個分而治之的方法。

事實上,在矩陣下,這並不困難,因為我們知道矩陣可以分為較小的子矩陣。

enter image description here

得到如下結果:

enter image description here

再一次,同樣的複雜性——我們得到了8個產出和4個和。

當然,為了獲得更快的解決方案,我們看一下1969年Strassen所做的。他定義了P1,P2,P3,P4,P5,P6和P7如下圖。

enter image description here

複雜度

Strassen的演算法比一般矩陣乘法演算法稍微快一些。一般的演算法的時間複雜度是O(n ^ 3),而Strassen的演算法的複雜度是O(n ^ 2.80)。

你可以看到在下面的圖表速度只是稍微快一些,即使對於大的n。

enter image description here

應用

儘管比電腦科學,這個演算法似乎更接近純數學。無論在哪使用NxN的陣列,我們都可以從矩陣乘法中受益。

另一方面Strassen的演算法並不比一般的n ^ 3矩陣乘法演算法快多少。維度對於小n(通常是n < 45)的問題,一般演算法是更好的選擇。然而從圖中可以看出,當n > 100以上是,差別還是非常大的。

當我們談論鄰接矩陣圖| V | = n時,通常使用NxN陣列,一些圖表的演算法實際上取決於矩陣乘法。

原文地址:http://www.stoimen.com/blog/2012/11/26/computer-algorithms-strassens-matrix-multiplication/

作者:Stoimen

相關文章