性能評価:特定値のインデックス抽出

C++言語で記述したプログラムと、アセンブリ言語で記述した関数を利用したときの性能差を検証してみましょう。
arques.hatenablog.com

符号付64ビット整数型

性能評価プログラム

C++で記述した関数と、アセンブリ言語で記述した関数を複数回呼び出します。それぞれに要した時間をclock関数で計測し、性能を評価します。common.hやアセンブリ言語で記述した関数は「特定値のインデックス抽出」で示したものと同じです。以降に、呼び出し側のソースリストを示します。

#include "..\common.h"  // TEMPLATES

#define T long long
extern "C"
{
    int aextIdxSQ(const T*, int*, const T, const size_t);
}

int main(void)
{
    const size_t ArrLen = 32768;
    static_assert(ArrLen % 16 == 0,
        "number of elements must be an integral multiple of 16.");
    const T cmpValue = -10;

    try
    {
        int cLen, aLen;
        T* a = (T*)_mm_malloc(sizeof(T) * ArrLen, 64);
        int* cIdx = (int*)_mm_malloc(sizeof(int) * ArrLen, 64);
        int* aIdx = (int*)_mm_malloc(sizeof(int) * ArrLen, 64);

        cout << "cmpValue = " << cmpValue << endl;
        clock_t start;

        #define LOOPS   10000
        init(a, ArrLen);

        start = clock();
        for (int j = 0; j < LOOPS;j++)
            cLen = cextIdx  (a, cIdx, cmpValue, ArrLen);
        print_elTime("cpp: ", start, clock());

        start = clock();
        for (int j = 0; j < LOOPS;j++)
            aLen = aextIdxSQ(a, aIdx, cmpValue, ArrLen);
        print_elTime("asm: ", start, clock());

        verify(cLen, aLen, cIdx, aIdx, ArrLen);

        _mm_free(aIdx);
        _mm_free(cIdx);
        _mm_free(a);
    }
    catch (char* str)
    {
        cerr << str << endl;
    }
    return 0;
}

これまでと同様に、時間の計測を行います。上記プログラムへ /O2 オプションを指定してビルド&実行したときの性能を示します。

アセンブリ言語で開発した関数は、C++言語で開発した関数より約5.4倍高速です。

符号なし64ビット整数型


アセンブリ言語で開発した関数は、C++言語で開発した関数より約5.2倍高速です。

符号付16ビット整数型


アセンブリ言語で開発した関数は、C++言語で開発した関数より約9.2倍高速です。

符号なし16ビット整数型


アセンブリ言語で開発した関数は、C++言語で開発した関数より約11.0倍高速です。

64ビット浮動小数点型


アセンブリ言語で開発した関数は、C++言語で開発した関数より約6.8倍高速です。

32ビット浮動小数点型


アセンブリ言語で開発した関数は、C++言語で開発した関数より約12.5倍高速です。