特征矩阵乘法比cblas慢吗?
我使用下面的代码来测试Eigen性能。特征矩阵乘法比cblas慢吗?
#include <iostream>
#include <chrono>
#define EIGEN_NO_DEBUG
#include <eigen3/Eigen/Dense>
#include <cblas.h>
using namespace std;
using namespace std::chrono;
int main()
{
int n = 3000;
high_resolution_clock::time_point t1, t2;
Eigen::MatrixXd A(n, n), B(n, n), C(n, n);
t1 = high_resolution_clock::now();
C = A * B;
t2 = high_resolution_clock::now();
auto dur = duration_cast<milliseconds>(t2 - t1);
cout << "eigen: " << dur.count() << endl;
t1 = high_resolution_clock::now();
cblas_dgemm(CblasColMajor, CblasNoTrans, CblasNoTrans,
n, n, n, 1.0, A.data(), n, B.data(), n, 1.0, C.data(), n);
t2 = high_resolution_clock::now();
dur = duration_cast<milliseconds>(t2 - t1);
cout << "cblas: " << dur.count() << endl;
return 0;
}
我用下面的命令编译:
g++ test.cpp -O3 -fopenmp -lblas -std=c++11 -o test
的结果是:
征:1422毫秒
cblas:432毫秒
我在做什么错误?根据他们的基准,它应该更快。
的另一个问题是使用numpy的,我得到24毫秒
import time
import numpy as np
a = np.random.random((3000, 3000))
b = np.random.random((3000, 3000))
start = time.time()
c = a * b
print("time: ", time.time() - start)
说你使用cblas
提供的信息非常少,因为cblas
只是一个API。底层的BLAS库可能是netlib的BLAS,OpenBLAS,ATLAS,Intel MKL,Apple的Accelerate甚至EigenBlas ......考虑到你的测量结果,很明显你的基础BLAS是一个高度优化的,利用AVX + FMA +多线程。因此,为了公平比较,您还必须通过编译-march=native -fopenmp
来启用Eigen方面的这些功能,并确保您使用的是Eigen 3.3。那么表现应该差不多。
关于numpy,Warren Weckesser已经解决了这个问题。你可能已经想通了24ms来执行2*3000^3=54e9
在标准计算机上的浮点运算是不可能的。
谢谢,问题在于使用Eigen 3.2。我转向Eigen 3.3现在它是500反对350.我不知道我使用的是什么blas库,我安装了软件包libblas3和libblas-dev。以下是apt-cache搜索的说明:libblas3 - 基本线性代数参考实现,共享库,libblas-dev - 基本线性代数子例程3,静态库 –
使用Eigen 3.2编译时使用-march = native不会改变任何内容,但如果我使用Eigen 3.3编译没有这个选项,它运行速度慢得多 –
你使用的是什么版本的Eigen和g ++? –
对于numpy数组,'*'是* element-wise *乘法。将'c = a * b'更改为'c = a.dot(b)'。或者,如果您使用的是足够新版本的Python 3和numpy,则可以编写'c = a @ b'。 –
Avi Ginsburg,Eigen版本3.2,g ++版本4.9.2,问题在于使用Eigen 3.2 –