0

一部の皆さんのおかげで、C++ での科学アプリの関数の 1 つの計算を高速化するために SSE を既に使用しており、 ints の巨大なベクトルを比較するために SSE 命令を使用しています

最適化された SSE 関数の最終バージョンは次のとおりです。

int getBestDiffsSse(int nodeId, const vector<int> &goalNodeIdTemp) {
    int positionNodeId = 2 * nodeId * nof;
    int myNewIndex = 2 * nof;
    int result[4] __attribute__((aligned(16))) = {0};

    __m128i vresult = _mm_set1_epi32(0);
    __m128i v1, v2, vmax;

    for (int k = 0; k < myNewIndex; k += 4) {
        v1 = _mm_loadu_si128((__m128i *) & distances[positionNodeId + k]);
        v2 = _mm_loadu_si128((__m128i *) & goalNodeIdTemp[k]);
        v1 = _mm_xor_si128(v1, vke);
        v2 = _mm_xor_si128(v2, vko);
        v1 = _mm_sub_epi32(v1, vke);
        v2 = _mm_sub_epi32(v2, vko);
        vmax = _mm_add_epi32(v1, v2);
        vresult = _mm_max_epi32(vresult, vmax);
    }
    _mm_store_si128((__m128i *) result, vresult);
    return max(max(max(result[0], result[1]), result[2]), result[3]);
}

どこ

const __m128i vke = _mm_set_epi32(0, -1, 0, -1);
const __m128i vko = _mm_set_epi32(-1, 0, -1, 0);

int* distances 
distances= new int[size];

サイズが大きい場合 (18M x 64)

私の素朴な質問は次のとおりです。a) 配列の距離が調整されているか、b) ベクトルの goalNodeIdTemp が調整されており、c) どうすればそれを行うことができますか?

memalign または align_malloc に関する投稿を見たことがありますが、それらを動的配列またはベクトルに使用する方法がわかりません。それともintについて話しているので、アライメントは問題ではありませんか? 私は Ubuntu 12.04 と gcc を使用しているため、Visual Studio コンパイラに関するソリューションはオプションではありません。

追加された質問: まず、次のコードは動的配列を調整するのに十分です (定義と初期化は別々に保持する必要があることに注意してください)。

int *distances __attribute__((aligned(16)));
distances = new int[size];

第 2 に、ベクトル goalNodeIdTemp を整列させるために、カスタム ベクトル アロケータのコード全体を記述する必要がありますか? より簡単な代替手段はありますか?

あなたの助けが必要です。前もって感謝します

4

1 に答える 1

1

パフォーマンスを少し改善するためにできることがいくつかあります。

  • ループから__m128i v1, v2, vmax;抜けますが、それはおそらくコンパイラによって行われます
  • 距離が適切に調整されていることを確認してください
  • std::vector を使用する代わりに、データを整列してポインターを渡します。次に、を使用します_mm_load_si128

distance と goalNodeIdTemp が適切に配置されていれば、未加工のポインターを使用できます。このようなもの :

__m128i *v1 = (__m128i *) & distances[positionNodeId + k];
__m128i *v2 = (__m128i *) & goalNodeIdTemp[k];

それ以上の最適化はすべて、アセンブリ コードを調べる必要があります。


a) 配列の距離が調整されている b) ベクトルの goalNodeIdTemp が調整されている場合、速度が向上すると思いますか?

はい、パフォーマンスがわずかに向上します。目を見張るものはありませんが、すべてのサイクルがカウントされると、目立つ可能性があります

それ、どうやったら出来るの?

整列させるgoalNodeIdTempには、特別なアロケータを使用する必要がありますstd::vector(たとえば、ここでその方法を参照してください)。

を揃えるdistanceには、少し注意が必要です。アラインされたメモリを割り当てる方法については、こちらを参照してください。

于 2013-07-25T11:45:00.287 に答える