矩阵相乘的两种方法
矩阵相乘最简单的形式就是一个三层循环,首先给出表示形式:C=A*B,其中A是左矩阵,是i*k的矩阵,B是右矩阵,是k*j的矩阵。
1)第一种方法就是以“行*列”的方式来计算,代码如下:
int leftMatrixRows,leftMatrixColumns,rightMatrixColumns; leftMatrixRows=leftMatrix.length;//i leftMatrixColumns=leftMatrix[0].length;//k rightMatrixColumns=rightMatrix[0].length;//j double[][] resultMatrix=new double[leftMatrixRows][rightMatrixColumns]; for (int i = 0; i < leftMatrixRows; i++) { for (int j = 0; j < rightMatrixColumns; j++) { for (int k = 0; k < leftMatrixColumns; k++) { resultMatrix[i][j] += leftMatrix[i][k] * rightMatrix[k][j]; } } }
运行时间是551s
2)第二种方法不是直接采用“行*列”的方式来计算,而是直接取出右矩阵的一行,分别与左矩阵的一个元素相乘,其实就是“行*行”的方式,,代码如下:
for (int i = 0; i < leftMatrixRows; i++) { for (int k = 0; k < leftMatrixColumns; k++) { for (int j = 0; j < rightMatrixColumns; j++) { resultMatrix[i][j] += leftMatrix[i][k] * rightMatrix[k][j]; } } }
运行时间是21s。比第一种方法快了很多,其实原因很简单,我们每次乘的时候,是从左矩阵取出一个元素,然后与右矩阵的一行的每个元素做乘法。二维数组在内存中的存放方式是行优先,也就是二位数组的一行中的各个元素是相邻存放的。然后就需要了解cpu中cache的作用,cache是cpu中的高速缓存,cpu从内存中取数据时,会将这个数据相邻的元素也取出来,存放在cache中。在这里,当我们将右矩阵某行的第一个元素与左矩阵的一个元素相乘时,cpu从内存中取到这个元素,并且将这个元素相邻的若干元素也读取到cache中,也就是将右矩阵这个行的其它元素也“顺道”读取到了cache中,节省了再去内存中读取数据的过程,自然速度就快了很多。