Search code examples
c++cc++11operator-overloadingmodulo

How to code a modulo (%) operator in C/C++/Obj-C that handles negative numbers


One of my pet hates of C-derived languages (as a mathematician) is that

(-1) % 8 // comes out as -1, and not 7

fmodf(-1,8) // fails similarly

What's the best solution?

C++ allows the possibility of templates and operator overloading, but both of these are murky waters for me. examples gratefully received.


Solution

  • First of all I'd like to note that you cannot even rely on the fact that (-1) % 8 == -1. the only thing you can rely on is that (x / y) * y + ( x % y) == x. However whether or not the remainder is negative is implementation-defined.

    Reference: C++03 paragraph 5.6 clause 4:

    The binary / operator yields the quotient, and the binary % operator yields the remainder from the division of the first expression by the second. If the second operand of / or % is zero the behavior is undefined; otherwise (a/b)*b + a%b is equal to a. If both operands are nonnegative then the remainder is nonnegative; if not, the sign of the remainder is implementation-defined.

    Here it follows a version that handles both negative operands so that the result of the subtraction of the remainder from the divisor can be subtracted from the dividend so it will be floor of the actual division. mod(-1,8) results in 7, while mod(13, -8) is -3.

    int mod(int a, int b)
    {
       if(b < 0) //you can check for b == 0 separately and do what you want
         return -mod(-a, -b);   
       int ret = a % b;
       if(ret < 0)
         ret+=b;
       return ret;
    }