{"id":16792290,"url":"https://github.com/chrivers/xmas-challenge","last_synced_at":"2025-10-13T17:34:04.976Z","repository":{"id":140207811,"uuid":"49200912","full_name":"chrivers/xmas-challenge","owner":"chrivers","description":"Xmas challenge","archived":false,"fork":false,"pushed_at":"2016-02-03T18:23:53.000Z","size":179,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-03-17T02:15:18.839Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/chrivers.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2016-01-07T11:33:16.000Z","updated_at":"2016-09-08T23:37:20.000Z","dependencies_parsed_at":"2023-04-26T09:31:30.359Z","dependency_job_id":null,"html_url":"https://github.com/chrivers/xmas-challenge","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/chrivers/xmas-challenge","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chrivers%2Fxmas-challenge","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chrivers%2Fxmas-challenge/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chrivers%2Fxmas-challenge/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chrivers%2Fxmas-challenge/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/chrivers","download_url":"https://codeload.github.com/chrivers/xmas-challenge/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chrivers%2Fxmas-challenge/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":279016284,"owners_count":26085828,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-10-13T02:00:06.723Z","response_time":61,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-10-13T08:45:19.249Z","updated_at":"2025-10-13T17:34:04.956Z","avatar_url":"https://github.com/chrivers.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# xmas-challenge\n\nChallenge: Write the smallest possible program (minus whitespace) that\noutputs the lyrics to \"12 Days of Christmas\"\n\nMy friend Espen Højsgaard made a public challenge to write the\nsmallest such program, and these are my contributions to that.\n\nThe rules are:\n\n  1. Can't read data files\n  2. Must finish in reasonable time\n  3. Whitespace characters do not count\n  4. The output is case-sensitive\n\nThe file full-lyrics.txt contains the lyrics reference. The script\n\"size.py\" takes the name of a file as the first argument, and prints\nthe number of non-whitespace characters in it.\n\nThere are 3 categories, and this is my attempt at winning each of those:\n\n  1. Shortest program, not counting whitespace\n\n  2. Shortest program, counting all characters including whitespace\n\n  3. Shortest program that consists only of whitespace.\n\n## xmas1\n\nThis is a pure-python implementation that originally wasn't very\nsmall. This is what lead me to pursue the other implementations. Since\nthen, it has been much improved. I would be surprised if a\nsignificantly smaller honest python solution exists.\n\n## xmas2\n\nThis slightly bends the rules, since it reads its own source code, but\nno external files are used. This is a rather trivial use of zlib\ncompression to try and minimize the size.\n\n## xmas3\n\nThis is a smaller version of xmas2, written in shell code, but since\nit uses HEREDOC format, it does NOT read its own code, thereby\navoiding the rule-bendiness. It only runs in zsh, since other shells\nbarf at the binary heredoc. The gzip blob was hand-optimized by\nlooking at all the possible outputs of -1 through -9. It turns out, -5\nwas the smallest output for this particular (small) input file. As an\nadded trick, heredocs do not need to be terminated, if they end at the\nend-of-file. So we save another couple of bytes there.\n\n## xmas4\n\nFor the \"smallest program, not counting whitespace\" category, the\ntrick is clearly to put as much information as possible into\nwhitespace, through whatever means necessary. This python script does\nnot use any file input tricks - instead, it encodes the lyrics into a\nstring constant consisting of whitespace and tab (\\t), which is then\ndecoded and printed. Since whitespace does not count, only the\ndecoding logic counts toward the size.\n\n## xmas5\n\nOriginally, the rules simply said \"smallest program, not counting\nwhitespace\", but since several contestants (including myself)\nimplemented a solution in the Whitespace language, this became\nsomewhat boring. For that reason, the \"smallest program consisting\nentirely of whitespace\" category was added, and this is my\ncontribution to that.\n\nThe trivial implementation in whitespace will simply push each\ncharacter to the stack, then print it. However, this takes about 43kb,\nwhich is clearly not ideal. So to be competitive, I implemented my own\nwhitespace assembler (since whitespace is really a machine language,\nnot a programming language). With it, I was able to create a\npartially-generated solution which employs hand-optimized whitespace\nassembler. That's not something you see every day, you have to admit.\n\nTo further bring the size down, I employ a number of tricks:\n\n - Create a callable write_buffer() routine, to output strings of\n   characters. This saves many, many \"write\" operations.\n\n - Numbers in whitespace are implemented as arbitrary *bit*\n   width. This means that instead of simply outputting 8 bits per\n   character (which is entirely valid), leading zeroes can be\n   discarded, leading to a saving of 1 byte per bit discarded this way.\n\n - Because storage size relates roughly to log_2(n), bringing down the\n   average absolute size of the numbers (characters) will save\n   space. Therefore, characters are offset-encoded at an ord('a')\n   offset, meaning that most lower-case letters become very small numbers.\n\n - A custom routine is implemented to print the \"On the nth day of\n   Christmas\" line efficiently.\n\n - A main routine is implemented, using a hand-written loop over the\n   various parts, meaning redundancy is kept to an absolute minimum.\n\n - Implemented double mean-offset-encoding for the character\n   literals. This saved a good number of bits in the numbers,\n   corresponding to an equal number of bytes saved in the output.\n\n## xmas6\n\nThe xmas4 solution was clearly a step in the right direction. I'm\nquite proud to have gotten the python solution down to the size I\nmanaged, but python tends to have verbose labels, so I reimplemented\nthe same basic idea in zsh, which approaches line noise as you move\ninto the more advanced features. Using short-form loops, default\nvariable values, and a ton of parameter expansion tricks, I was able\nto save a number of bytes over the python solution.\n\n## xmas7\n\nThis is an iteration on xmas3, which competes in the \"smallest total\nsize\" category. Since we are dealing with a shell script that decodes\ngzip data, I was wondering if maybe there wasn't some padding data at\nthe end of the gzip data stream. It turns out there is! And luckily,\nthis particular stream is still decompressible if you shave a few\nbytes off. So xmas7 is just xmas3 without the last few bytes at the end.\n\n## xmas8\n\nIn the \"whitespace does not count\" category, the trick is clearly to\npack as much information as possible into a whitespace encoding, and\nwhite the simplest (smallest) possible decoder to extract it. I\nnoticed that perl has some very compact operators, so I re-implemented\nxmas6 in perl, getting the size down to 24 bytes. Along the way I\ndiscovered that perl's binary unpacking only cares about 1's. If you\nuse space for zeroes, it still works fine (which is bordering on\nabsurd). This saved another byte.\n\n## xmas9\n\nWhen writing the smallest possible decoder, it obviously helps to use\na language designed to be as compact as possible. Here's my entry of\nthe same idea again, but this time in CJam, a code golf language\ndesigned for extreme compactness. This got the size down to 9 bytes!\n\n## xmas10\n\nFinally, after making xmas9, I scoured the net for other esoteric golf\nlangauges that would allow me to write things even more compactly. I\nfound \"gs2\", which is a pythyn-based extremely compact stack-based\ngolfing language. It's wonderfully bizarre - it even has multiple\nkinds of end quotes! With this, I managed to bring the size down to\njust 5 bytes.\n\nIf we assume that a string needs to be quoted (or otherwise have\nbeginning and end marked), and that we need at least 1 operation to go\nfrom whitespace encoding to ascii, this brings the reasonable\ntheoretical minimum size to 3 bytes. And that requires that the\nlanguage more or less contains a \"convert from whitespace encoding to\nascii and print the result\" operator. I'm quite satisfied with this\nresult.","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fchrivers%2Fxmas-challenge","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fchrivers%2Fxmas-challenge","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fchrivers%2Fxmas-challenge/lists"}