2016-09-25 20 views
0

私は、(固定サイズの)対角線に沿ったブロックを除いて、疎な行列を持っているとしましょう。Eigenで効率的なブロックスパース行列の乗算

Eigen::SparseMatrix<float> lhs;

LHS約2%の非スパースであるが、非常に大きくてもよいです。それでは、私はベクトルを持っているとしましょう:瞬間のために

Eigen::MatrixXf rhs = Eigen::MatrixXf::Random(SomeSz, 1);

、のは、それは密だと仮定しましょう。

私は効率的に計算したい

result.noalias() = lhs * rhs;

私は(クラン付き)-O3 -march =ネイティブ-mtune =ネイティブでコンパイルした場合、これは最適な結果をもたらすのでしょうか? RHSがスパース何だった場合にも

、:

Eigen::SparseMatrix<float> rhs; rhs.resize(SomeSz, 1); rhs.reserve(SomeSz/SomeFactor);

です:

result = lhs * rhs;

まだ最適/次善の?

私は、Eigenがブロック疎構造を利用し、必要な計算のみを実行するかどうかを尋ねています。

答えて

0

まず、rhsの密な場合、rhsがベクトルの場合、VectorXfを使ってEigenに伝えてください。次に、Eigen 3.3では、-fopenmpでコンパイルし、lhsの行主記憶域を使用してマルチスレッドを利用できます。

稀なケースでは、はいEigenはlhsとrhsの両方の希薄さを考慮に入れます。複雑さは実際にrhs.nonZeros()*average_nnz_per_col_of_lhsになりますが、濃いrhsのrhs.size()*average_nnz_per_col_of_lhsとは対照的です。だからrhsが本当に疎であれば、試してみる価値があるかもしれません。有用な列のlhsのみが考慮されます。この場合、lhsコラムメジャーをよく保ちます。