在 ARM 上快速搜索/替换 8 位数组中匹配的单个字节

Fast search/replace of matching single bytes in a 8-bit array, on ARM

本文关键字:数组 字节 单个 ARM 搜索 替换      更新时间:2023-10-16

我开发图像处理算法(使用GCC,针对ARMv7(Raspberry Pi 2B))。

特别是我使用一个简单的算法,它更改掩码中的索引:

void ChangeIndex(uint8_t * mask, size_t size, uint8_t oldIndex, uint8_t newIndex)
{
    for(size_t i = 0; i < size; ++i)
    {
        if(mask[i] == oldIndex)
            mask[i] = newIndex;
    }
}

不幸的是,它的目标平台性能很差。

有什么方法可以优化它吗?

ARMv7 平台支持称为 NEON 的 SIMD 指令。通过使用它们,您可以更快地编写代码:

#include <arm_neon.h>
void ChangeIndex(uint8_t * mask, size_t size, uint8_t oldIndex, uint8_t newIndex)
{
    size_t alignedSize = size/16*16, i = 0;
    uint8x16_t _oldIndex = vdupq_n_u8(oldIndex);
    uint8x16_t _newIndex = vdupq_n_u8(newIndex);
    for(; i < alignedSize; i += 16)
    {
        uint8x16_t oldMask = vld1q_u8(mask + i); // loading of 128-bit vector
        uint8x16_t condition = vceqq_u8(oldMask, _oldIndex); // compare two 128-bit vectors
        uint8x16_t newMask = vbslq_u8(condition, _newIndex, oldMask); // selective copying of 128-bit vector
        vst1q_u8(mask + i, newMask); // saving of 128-bit vector
    }
    for(; i < size; ++i)
    {
        if(mask[i] == oldIndex)
            mask[i] = newIndex;
    }
}