In case you grow tired of clear-written, understandable code, obfuscation contests provide a nice change of scenery, and trying to make sense of their entries can be a fun-time activity and an interesting alternative to the usual brainteasers. If we ever happen to see a Simpsons episode on the subject, [Andy Sloane] has the obvious candidate for a [Hackerman Homer] entry: a rotating ASCII art donut, formatted as donut-shaped C code.
The code itself actually dates back to 2006, but has recently resurfaced on Reddit after [Lex Fridman] posted a video about it on YouTube, so we figured we take that chance to give some further attention to this nifty piece of art. [Andy]’s blog article goes in all the details of the rotation math, and how he simply uses ASCII characters with different pixel amounts to emulate the illumination. For those who prefer C over mathematical notation, we added a reformatted version after the break.
Sure, the code’s donut shape is mainly owed to the added filler comments, but let’s face it, the donut shape is just a neat little addition, and the code wouldn’t be any less impressive squeezed all in one line — or multiple lines of appropriate lengths. However, for the actual 2006 IOCCC, [Andy] took it a serious step further with his entry, and you should definitely give that one a try. For some more obfuscated shell animations, check out the fluid dynamics simulator from a few years back, and for a more recent entry, have a look at the printf Tic Tac Toe we covered last month.
int k; double sin(); double cos(); main() { float A=0; float B=0; float i; float j; float z[1760]; char b[1760]; printf("\x1b[2J"); for (;;) { memset(b, 32, 1760); memset(z, 0, 7040); for (j = 0; 6.28 > j; j += 0.07) { for (i = 0; 6.28 > i; i += 0.02) { float c = sin(i); float d = cos(j); float e = sin(A); float f = sin(j); float g = cos(A); float h = d + 2; float D = 1 / (c * h * e + f * g + 5); float l = cos(i); float m = cos(B); float n = sin(B); float t = c * h * g - f * e; int x = 40 + 30 * D * (l * h * m - t * n); int y = 12 + 15 * D * (l * h * n + t * m); int o = x + 80 * y; int N = 8 * ((f * e - c * d * g) * m - c * d * e - f * g - l * d * n); if (22 > y && y > 0 && x > 0 && 80 > x && D > z[o]) { z[o] = D; b[o] = ".,-~:;=!*#$@"[N > 0 ? N : 0]; } } } printf("\x1b[H"); for (k = 0; 1761 > k; k++) { putchar(k % 80 ? b[k] : 10); } A += 0.04; B += 0.02; } }
If you want to slow down (or speed up) the animation, decrease (or increase) the values added to A
and B
at the very end of the loop. Keep them in the same proportion to retain the rotation animation, or just play around with them and see what happens.
Remember to link against the Math library with -lm
when compiling.
[via /r/programming]
If you were on the “shorter lines means cleaner code” side in the Linus 80-char line length hullaballoo, I give you this.
Two things: aalib and bb demo.
I think that’s against the IOCCC rules.
C programmers were put here by a higher power, the great computer in the Sky
More awesome textmode animations: http://tmdc.scene.org/ (a demoscene competition that’s been running off and on for years)
Cool!