4

インテル® MKL ライブラリーが提供する Boost::uBLAS インターフェイス (mkl_boost_ublas_matrix_prod.hpp を含む) を使用して行列乗算を実行するための実験を行っています。私のデータは単なる整数であるため、マトリックス テンプレートの型を int に変更しようとしたところ、パフォーマンスが大幅に低下しました。主に、利用可能な 12 コアではなく 1 つの CPU コアのみを使用するコードが原因のようです。MKL ドキュメントには、整数が MKL の OpenMP マルチスレッド機能を使用していない理由を説明するものは見つかりませんでした (MKL をまったく使用していなかったと思いますか?)。

さらに、フロートと比較した場合、ダブルでは 50% のパフォーマンス ヒットが見られます。

質問:

  1. float と double の違いはなぜですか?
  2. 整数を使用できないのはなぜですか?

以下のコードからの私の結果は次のとおりです。

  matrix<float>(10000x10000):  13 seconds (12 threads used)
 matrix<double>(10000x10000):  26 seconds (12 threads used)
    matrix<int>(10000x10000):  >1000 seconds (1 thread used, stopped early)
  matrix<float>(25000x25000): 187 seconds (12 threads used)
 matrix<double>(25000x25000): 401 seconds (12 threads used)

使用されるコード (必要に応じて両方の matrix< type > 行を置き換えます):

#include <boost/numeric/ublas/matrix.hpp>
#include <mkl_boost_ublas_matrix_prod.hpp>

using namespace boost::numeric::ublas;

void benchmark() {

    int size = 10000;
    matrix<float> m(size, size);
    for (int i = 0; i < size; ++i) {
        for (int j = 0; j < size; ++j) {
            m(i,j) = 2*i-j;
        }
    }
    matrix<float> r(size, size);
    r = prod(m,m);
}

int main(int argc, char *argv[]) {
    benchmark();
    return 0;
}

以下でコンパイル:

 g++ Flags: -std=c++0x -O3 -DNDEBUG -DMKL_ILP64  -m64 -msse4.2 -march=native -mtune=native
 ld Flags:  -lmkl_intel_ilp64 -lmkl_gnu_thread -lmkl_core -fopenmp -lpthread -lm

プロセッサー:

 Intel Xeon E7530 with 6 Cores (x2) with HT. 

MKL は何の役にも立たないと彼らが言うようにハイパースレッドを使用しないので、24 ではなく 12 のスレッドを使用できます。

4

1 に答える 1

7

float と double の違いはなぜですか?

最新の CPU は、ベクトル命令を使用して浮動小数点演算を実行します。これらの命令のスループットと長さは固定されています。たとえば、Intel Xeon E7530 の各コアは、サイクルごとに 2 つの 128 ビット加算または乗算を処理できます。これにより、サイクルごとに 4 つの double または 8 つの float が発生します。

整数を使用できないのはなぜですか?

ublas の例のテンプレートは、float および double テンプレートの行列乗算を MKL SGEMM および DGEMM 関数にマップします。行列テンプレートを float/double から int に変更すると、MKL は整数行列乗算をサポートしないため、BOOST は行列乗算の参照実装を使用します。

于 2012-08-01T10:11:30.343 に答える