【算法设计与分析】【C++】斯特拉森Strassen矩阵乘法加速
矩阵乘法加速原理
- 简单地来说,就是把普通矩阵的八次乘法优化成七次乘法,我们可以直接按照上面给出的式子
来写。 - 但是需要注意的是,进行矩阵分块和矩阵合并也需要消耗计算资源,显然在矩阵非常小时,乘法消耗的时间远小于各种分块后再计算的时间,因此程序中的BORDER_SIZE的选择对于程序的运行影响极大,经过本人测试下来,128是比较的好的数据
- 接下来上代码(本代码仅限于n*n的矩阵并且n为2的幂次方)
/*
author : TheSun
Time : 2022-03-04 00:44:17
*/
#include<bits/stdc++.h>
using namespace std;
const int BORDER_SIZE = 128; //在这个数量下面使用普通乘法,因为此时各种赋值所消耗的时间大于乘法运算的时间
struct Matrix
{
int r, c;
int **v;
Matrix(int x=0 , int y=0);
Matrix(const Matrix& others);
~Matrix();
int* operator[](int n);
Matrix operator *(Matrix others);//重载为加速矩阵乘法
inline void setSize(int x , int y);
inline void operator=(Matrix others);
void Print();
inline Matrix operator+(Matrix& others);
inline Matrix operator-(Matrix& others);
inline Matrix Muti(Matrix& others); //普通矩阵乘法
inline void MatrixDiv(Matrix& A_11 , Matrix& A_12 , Matrix& A_21 , Matrix& A_22); // 矩阵分块
inline Matrix MergeMatrix(Matrix& A_11 , Matrix& A_12 , Matrix& A_21 , Matrix& A_22); //合并矩阵
//bool oprator==()
};
Matrix::Matrix(const Matrix& others)
{
//if()
r = others.r , c = others.c;
v = new int *[r + 1];
for(int i=0 ; i<=r ; ++i)
v[i] = new int [c + 1];
for(int i=1 ; i<=r ; ++i)
for(int j= 1 ; j<=c ; ++j)
v[i][j] = 0;
}
Matrix Matrix::operator*(Matrix others)
{
if( r <= BORDER_SIZE && c <= BORDER_SIZE && others.c <= BORDER_SIZE)
{
return this->Muti(others);
}
else
{
Matrix A_11(r/2 , c/2) , A_12(r/2 , c/2) , A_21(r/2 , c/2) , A_22(r/2 , c/2),
B_11(others.r/2 , others.c/2) , B_12(others.r