C++ 有没有办法用AVX2写mm256 shldi epi8(a,b,1)?(向量之间每8位元素移动一位)

C++ 有没有办法用AVX2写mm256 shldi epi8(a,b,1)?(向量之间每8位元素移动一位),c++,avx,avx2,C++,Avx,Avx2,我需要将b的每个元素的顶部位移到a的相应元素的底部,就像计数为1一样 有人知道这样转变的方法吗 例如: __m256i x = { 11001100, 00110011, 11001100, 00110011,... x16 } __m256i y = { 10111100, 10001011, 11000010, 01100111,... x16 } __m256i res = _mm256_shldi_epi16(x,y); 那么res包含: 10011001011001111001100

我需要将b的每个元素的顶部位移到a的相应元素的底部,就像计数为1一样

有人知道这样转变的方法吗

例如:

__m256i x = { 11001100, 00110011, 11001100, 00110011,... x16 }
__m256i y = { 10111100, 10001011, 11000010, 01100111,... x16 }
__m256i res = _mm256_shldi_epi16(x,y);
那么res包含:

10011001011001111001100101100110,…x16


编者按:之前的问题将此描述为_mm256_sllv_epi8。sllv是一种可变计数移位,其中每个元素的计数来自另一个源中的对应元素,与双移位完全不同。

显然,任务是将a中的字节向左移位1,同时从b中的对应字节向上移位,就像固定距离为1的微小漏斗移位。左移可以通过字节加法完成,然后从b复制该位:

这个案子有个变通办法
__m256i funnel_left1_epi8(__m256i a, __m256i b) {
    __m256i a2 = _mm256_add_epi8(a, a);
    __m256i bit_from_b = _mm256_and_si256(_mm256_srli_epi16(b, 7), _mm256_set1_epi8(1));
    return _mm256_or_si256(a2, bit_from_b);
}