2147483647

2015-02-12, Comments

Magic!

When software developers refer to “magic numbers” they mean those numeric literals which appear in a program without explanation — as if by magic. Consider the mysterious figures in this incantation:

int cigarettes()
{
    return 365 * 20 * 10 + 2 * 20 + 17;
}

Why is the 20 repeated? Does the first 20 mean the same as the second one? Could 365 be the number of days in a year? Named constants would make the code easier to read and maintain.

Some numbers truly are magical though.

2147483647

The number 2147483647 is special and terrible.

It’s a substantial number, far greater than the number of goals Lionel Messi has scored or the number of hot dinners I’ve eaten, and comparable with the number of heart beats in a lifetime or the number of instructions a processor executes in a second; but it’s not that large. You’ll need more than 2147483647 bytes to install a modern operating system, let alone store your video collection. And shuffling a pack of just 52 cards has 80658175170943878571660636856403766975289505440883277824000000000000 possible outcomes.

If 2147483647 isn’t remarkable for its size it certainly has a noteworthy history. In 1772 the Swiss mathematician Leonhard Euler proved it a prime. I’m guessing it was the largest known prime at the time. Euler didn’t have a computer to hunt for primes so he narrowed the field by focusing on Mersenne numbers — numbers one less than a power of two — a strategy which remains a winner even today, when computers are networked to search.

Actually, 2147483647 is a double Mersenne prime, which is to say it takes the form 2m - 1, where m itself takes the form 2n - 1.

>>> 2**(2**5 - 1) - 1
2147483647

Magic!

Dragons!

2147483647 has a special significance for C programmers, who know it by the name INT_MAX, and for C++ programmers, who demystify the digits as std::numeric_limits<int>::max().

Remember, 2147483647 is Mersenne(Mersenne(5)), which is Mersenne(31), or 2 to the power 31 minus 1. In binary arithmetic you add a zero on the right to multiply by 2 so 2 to the 31 is 1 followed by 31 zeros; and subtracting 1 leaves 31 1’s. It’s the largest signed value you can fit in a 32 bit register.

>>> mersenne31 = 2**31-1
>>> bin(mersenne31)
'0b1111111111111111111111111111111'
>>> hex(mersenne31)
'0x7fffffffL'
>>> mersenne31
2147483647L

It’s quite possible to inadvertantly increment an int which has reached INT_MAX. The result is undefined behaviour: anything could happen.

Gangnam Style

We never thought a video would be watched in numbers greater than a 32-bit integer (=2,147,483,647 views), but that was before we met PSY. Gangnam Style has been viewed so many times we had to upgrade to a 64-bit integer (9,223,372,036,854,775,808)!

youtube developers

Psy

Exactly what undefined behaviour was provoked when PSY’s popularity broke the magic limit isn’t disclosed. Maybe a server leaked account details to North Korean hackers. Or maybe the video’s viewing figures were wrong for a while.

Note that the new limit of 9,223,372,036,854,775,808 is an unsigned value, which is exempt from this flavour of undefined behaviour and wraps to zero when you bump it up.

Bugwards compatibility

There’s another reason for preferring INT_MAX to the magical 2147483647: the two values might be different. 2147483647 is 2147483647 but INT_MAX depends on the implementation.

A modern computer probably has 64 bit registers making a 64 bit int a more natural choice. However, for compatibility reasons, ints may intentionally be limited to 32 bits!