3

我有一个包含一些 int 值的数组([position%2=0] 处的值为负,[position%2=1] 处的值为正)。

我想以 4 步将这些值从数组加载到寄存器,但我希望它们反转(正转换为负,反之亦然)

__m128i v1;
for (int k = 0; k < limit; k += 4) {
        v1 = _mm_load_si128((__m128i *) & myArray[position + k]);
}

上面的 SSE 代码将值按原样加载到寄存器中:是否有命令取 v1 并反转它?可以一步/命令完成吗?甚至可以直接从原始数组加载值吗?

任何帮助将不胜感激。提前致谢。

4

2 回答 2

4

假设你的整数元素是 32 位,那么你可以从 0 中减去,例如

v1 = _mm_load_si128(...);                   // load data
v1 = _mm_sub_epi32(_mm_set1_epi32(0), v1);  // negate all elements
于 2013-08-30T15:21:10.703 回答
2

另一种方法是:

__m128i v1 = _mm_xor_si128(
    _mm_load_si128((__m128i *)&myArray[position + k]), 
    _mm_cmpeq_epi8(v1, v1)
);

基本上我们正在这样做:x ^ -1假设我们使用的是带有二进制补码的机器,所以 -1 是一个全1的序列......

请注意以下内容,其中~表示反转,^表示异或。

~0 == 1 == (0 ^ 1)
~1 == 0 == (1 ^ 1)

_mm_cmpeq_epi8(a, a)将在您可以使用时设置所有 1 _mm_set1_epi32(-1),它实际上可能会更慢,因为它可能会生成内存访问,如果性能是一个问题,我建议进行分析......

于 2014-07-30T20:57:31.677 回答