2017-02-24 21 views
1

AVX2ベクトルを定数で除算したい。私はthis questionと他の多くのページを訪問しました。何かを助けて助けてくれると思ったのですが、私は理解しませんでした。だから問題は、この部門はボトルネックです。 AVX命令を使用して操作をフロートして行うために、鋳造、__m256iベクトルを整数変数で分ける方法は?

まず:私は、2つの方法を試してみました最初の方法では

//outside the bottleneck: 
__m256i veci16; // containing some integer numbers (16x16-bit numbers) 
__m256 div_v = _mm256_set1_ps(div); 

//inside the bottlneck 
//some calculations which make veci16 
vecps = _mm256_castsi256_ps (veci16); 
vecps = _mm256_div_ps (vecps, div_v); 
veci16 = _mm256_castps_si256 (vecps); 
_mm256_storeu_si256((__m256i *)&output[i][j], veci16); 

、問題がある:分裂せずに経過時間5nsのであり、この経過時間であります約60ns。

第二には、私は、配列に格納し、このようにそれをロード:

int t[16] ; 
inline __m256i _mm256_div_epi16 (__m256i a , int b){ 

    _mm256_store_si256((__m256i *)&t[0] , a); 
    t[0]/=b; t[1]/=b; t[2]/=b; t[3]/=b; t[4]/=b; t[5]/=b; t[6]/=b; t[7]/=b; 
    t[8]/=b; t[9]/=b; t[10]/=b; t[11]/=b; t[12]/=b; t[13]/=b; t[14]/=b; t[15]/=b; 
    return _mm256_load_si256((__m256i *)&t[0]);   
} 

まあ、それは良かったです。しかし、まだ経過時間は17nsです。計算があまりにも多くここに表示されます。

質問:このインライン関数を最適化する方法はありますか?

+0

なぜ投票するのですか? – Martin

+1

私の議決権行使ではありませんが、おそらく['_mm256_mulhrs_epi16'](https://software.intel.com/sites/landingpage/IntrinsicsGuide/#text=_mm256_mul&expand=3710)が必要です。これは固定小数点乗算を行うので、被乗数ベクトルを '32768/b'に設定するだけです。 –

+0

これは乗算です。私はそれを分けたい。 – Martin

答えて

4

_mm256_mulhrs_epi16でこれを行うことができます。これはb > 1を前提としていること

inline __m256i _mm256_div_epi16 (const __m256i va, const int b) 
{ 
    __m256i vb = _mm256_set1_epi16(32768/b); 
    return _mm256_mulhrs_epi16(va, vb); 
} 

注:あなただけ32768/bに被乗数ベクトルを設定するので、これは、固定小数点の乗算を行います。

+1

この回答は素晴らしいです、違反はありません経過時間は5nsです。 – Martin

関連する問題