【问题标题】:Optimization of bitwise & result按位和结果的优化
【发布时间】:2017-04-24 17:58:27
【问题描述】:

我正在读取一个停止位编码的数据流,我需要能够识别具有停止位的字节。

我的代码的 sn-p:

    const unsigned char *b; // Pointer to the datastream

    ...

    // Test the sign bit
->  if (*b & 0x40)
    {
        // Negative number, do relevant stuff
        ...
    }

    while(true)
    {
->      if (!(*b & 0x80))
        {
            // Not the stopbit
            ...
        }
        else
        {
            // Reached the stopbit, breaking out of the loop
            ...
            b++;
            break;
        }

        b++;
    }

这个函数在一个紧密的循环中运行,并且需要实时工作。我用箭头标记了分析器显示为“热”的行,它们是符号位和停止位的测试。

有什么想法可以优化这些操作(尤其是符号位测试,因为它似乎需要更多时间,即使它在循环之外)?

编辑: 之前应该提到过,指针 b 是在循环内部使用的,因此我不能在 while() 中迭代。

【问题讨论】:

  • 一次处理更多字节怎么样?用 0x8080808080808080 检查至少 8 个字节并回退到每字节循环应该很简单。
  • 我认为你的分析器在骗你。除非您省略的代码是 very 轻量级的,否则我看不出该位测试如何成为热点。唯一可能的问题是分支预测是否出错。您正在使用哪些优化级别?停止位多久出现一次?你能容忍添加编译器特定的提示来建议分支的发展方向吗?
  • 您可以尝试while (! (*b & 0x80)) - 然后在循环后执行停止位代码。汇编器是什么样的?
  • 你在为什么平台编译?你用的是什么编译器?这些是否适合实时要求?
  • 很可能(*b & 0x40) 是缓存未命中,从您介绍的内容来看,这是该内存块的第一次加载。没有足够的信息来建议改进。这可能是不可避免的

标签: c++ optimization


【解决方案1】:

我将摆脱while(true) 以及循环内的(附加)测试。 但我不确定这是否真的是问题所在,因为“不是停止位”代码很可能需要比位测试更长的时间。

unsigned char c = 1;
while ( !((c=*p++) & 0x80)) {
    // Not the stop bit stuff
    printf ("%d\n", c);
}
// stop bit reached stuff

【讨论】:

  • 可能之前应该提到过这个,但是指针是在循环内部使用的,我不能在while()中迭代它。我会在编辑中添加这个
猜你喜欢
  • 2013-07-14
  • 2011-10-11
  • 2023-03-10
  • 1970-01-01
  • 2012-08-10
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-10-24
相关资源
最近更新 更多