是否有更有效的方法来计算正模数?

时间:2014-04-10 09:20:36

标签: c++ modulo performance

C和C ++中的模数不以数学上正确的方式运行,因为它在执行负数的模数时返回负结果。在做了一些研究之后,似乎实现正确行为的经典方法是:

positive modulo(int i, int n)
{
   return ( ( (i % n) + n ) % n );
}

考虑模数在计算上是昂贵的,有没有更有效的方法来计算任何数字的正模数(我已经看到2的幂的解,但我需要通用的东西)?

谢谢,祝你有愉快的一天

3 个答案:

答案 0 :(得分:3)

这可能更慢或更快,具体取决于编译器,优化级别和架构:

static inline int modulo(int i, int n) {
  const int k = i % n;
  return k < 0 ? k + n : k;
}

它可能更慢的原因是条件操作可能引入一个分支,有时分支很慢。

答案 1 :(得分:1)

pts答案中的解决方案是最佳解决方案。即使分支机构出现减速,它也可能比分区更快。但是如果你真的需要避免分支

inline int modulo(int i, int n)
{
    int k = i % n;
    int a = -(k < 0);  // assuming 2's complement
    // or int a = ((k < 0) << (INT_SIZE - 1)) >> (INT_SIZE - 1); if your system doesn't use 2's complement
    return k + n & a;
}

答案 2 :(得分:0)

如果模数首先是模数,​​那么公式中的第二个模数只需要再次减去n。所以它应该至少只有有条件添加n的性能:

   auto m = (i % n);
   return (m < 0) ? m+n : m;