0

I have a two-dimesional integer array InArray[2][60] carrying short data in 2 LS bytes and bit field data in 2 MS bytes. Please suggest a faster method to extract short data and copy it to a short OutArray[60], something on the lines for memcpy(). I presume iterating through each item is not the most optimal method of doing this. TIA

EDIT : Adding code snippet

int InArray[2][60];
short OutArray[60];
for (int i=0; i < 60;i++)
{
    OutArray[i] = (short)(InArray[0][i] & 0xffff);
}

Is there a better and possibly faster way of doing this

4

2 回答 2

2

如果你真的要复制一个 60 元素的数组,那也没关系。

如果阵列更大和/或您经常这样做,那么您需要查看SIMD指令集:英特尔平台上的 SSEx,PPC 上的 Altivec ......

例如,使用 SSE4,您可以使用 _mm_packus_epi32() 将 2*4 32 位操作数打包(并饱和)成 8 个 16 位操作数。

您的编译器可能具有使用这些的内在函数:http: //msdn.microsoft.com/en-us/library/hh977022.aspx,http : //gcc.gnu.org/onlinedocs/gcc-3.3.6/gcc/PowerPC -AltiVec-Built_002din-Functions.html ...

于 2013-06-20T13:45:09.053 回答
1

如果您多次执行此类操作,这只会有所帮助。我使用 Agner Fog 的矢量类来做到这一点(http://www.agner.org/optimize/vectorclass.zip)。这是一个使用 SSE/AVX 的类。但是,如果您将标签 SSE 和 AVX 添加到您的问题中,您会找到最佳答案。

如果您可以确保数组是 16 字节或 32 字节对齐的,您还将获得更好的结果。在下面的代码中,它还有助于使数组的宽度等于 64(即使您只打算使用 60 个元素)或使数组的长度成为 64 的倍数。

#include <stdio.h>
#include "vectorclass.h"

void foo(int InArray[2][60],  short OutArray[60]) {
    for (int i=0; i < 60; i++) {
        OutArray[i] = (short)(InArray[0][i] & 0xffff);
    }
}

void foo_vec8s(int InArray[2][60],  short OutArray[60]) {
    int i=0;
    for (; i <(60-8); i+=8) {
        Vec8s v1 = Vec8s().load(&InArray[0][i]);
        Vec8s v2 = Vec8s().load(&InArray[0][i+4]);
        Vec8s out = blend8s<0,2,4,6,8,10,12,14>(v1,v2);
        out.store(&OutArray[i]);
    }
    //clean up since arrays are not a multiple of 64
    for (;i < 60; i++) {
        OutArray[i] = (short)(InArray[0][i] & 0xffff);
    }
}

int main() {
    int InArray[2][60];
    for(int i=0; i<60; i++) { 
        InArray[0][i] = i | 0xffff0000;
    }

    short OutArray1[60] = {0};
    foo(InArray, OutArray1);
    for(int i=0; i<60; i++) {
        printf("%d ", OutArray1[i]);
    } printf("\n");

    short OutArray2[60] = {0};
    foo_vec8s(InArray, OutArray2);
    for(int i=0; i<60; i++) {
        printf("%d ", OutArray2[i]);
    } printf("\n");  
}
于 2013-06-20T15:03:56.667 回答