I came across an intriguing C code that prints A + B
, but I have trouble understanding it.
A B
where A
, B
are integers between 0
and 10
separated by a single space.
main( n ) { gets( &n ); printf("%d", n % 85 - 43); }
This was intended for short coding, please don't mind the warnings.
gets( &n )
stores the ASCII values of A, space, and B in the lower three bytes of n
. For example, A = 3
and B = 8
would yield n = 0x00382033
. Given conditions prevent n
from overflowing. But I do not understand how n % 85 - 43
yields A + B
.
How do you come up with these numbers?
The modulus operator is added in the arithmetic operators in C, and it works between two available operands. It divides the given numerator by the denominator to find a result. In simpler words, it produces a remainder for the integer division. Thus, the remainder is also always an integer number only.
rem = num1 % num2; We calculate the remainder using the Modulus(%) operator. printf("Remainder = %d", rem); printf("Remainder = %d", rem);
Double Modulus Operator This kind of mod operator does not exist in C or C++ where the mod operator only works with int operands. The evaluated result is a double value. For example, 8.27 % 2 evaluates to 0.27 since the division is 4 with a remainder of 0.27.
With little-endian ints (and assuming ASCII text, and 8-bit bytes, and all the other assumptions the code requires), and ignoring all the technically-wrong-in-modern-C stuff in the code, your "What I understand so far" is correct.
gets(&n)
will store the ASCII values of A, space, and B into the first 3 bytes of n
. It'll also store a null terminator into the 4th byte. Storing those ASCII values into those bytes of n
results in n
taking the value B*256*256 + space*256 + A
, where B
, space
, and A
represent the corresponding ASCII values.
256 mod 85 is 1, so by the properties of modular arithmetic,
(B*256*256 + space*256 + A) % 85 = (B + space + A) % 85
Incidentally, with 4-byte big-endian ints, we get
(A*256*256*256 + space*256*256 + B*256) % 85 = (B + space + A) % 85
so endianness doesn't matter, as long as we have 4-byte ints. (Bigger or smaller ints could be a problem; for example, with 8-byte ints, we'd have to worry about what's in the bytes of n
that gets
didn't set.)
Space is ASCII 32, and the ASCII value for a digit character is 48 + the value of the digit. Defining a
and b
as the numeric values of the digits entered (rather than the ASCII values of the digit characters), we have
(B + space + A) % 85 = (b + 48 + 32 + a + 48) % 85 = (a + b + 128) % 85 = (a + b + 43) % 85 (B + space + A) % 85 - 43 = (a + b + 43) % 85 - 43 = (a + b) % 85 = a + b
where the last two equivalences rely on the fact that a
and b
take values from 0 to 9.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With