Py256
- Not to be confused with 256.
Py256 is a golfing language by User:Makonede. It uses Base-256 compression to encode long hexadecimal numbers representing programs. Py256 uses 05AB1E's SBCS for Base-256.
Article syntax
Functions will have a number next to them in the documentation. This is the arity, or number of arguments the function takes.
Syntax
Py256 programs start out as a long number. 0
is assigned End literal/argument list so that programs should never contain leading zeros and do not need a leading 1
to be compressed losslessly.
Commands and groups
Py256 uses prefix commands. Some commands come in groups. Commands in groups are used like so: GSC
, where G
is the group number, S
is the subgroup number, and C
is the command number. Here is the top-level command/group list:
0: End literal/argument list (for arbitrary arity functions) 1: Lambda (2) 2: Operators (simple math) 3: Builtins 4: Constants 5: ASCII-art 6: String literal (1) 7: Dictionary compression (1) 8: Numeric literal (1) 9: HTTP A: Python execution (1) B: I/O C: Statements and conditionals D: Advanced operators E: Elixir execution (1) F: Shell execution and escape character (1)
Command syntax
C
represents the command, and digits (excluding 0
) represent arguments.
Arbitrary arity (e.g. print): C123...N0 Fixed arity (e.g. +): C120
Lambda syntax
Lambdas are a bit different from the rest. The first argument is the number of arguments the lambda should take, in the form of a numeric literal 8...0
. Literal 0
s in the arity should be escaped with a prefixed F
, and literal F
s should be escaped with a prefixed F
as well. The rest is not really arguments, but instead code to execute when running the lambda. When running the lambda, the first A
lambda variables are set to the function arguments locally, where A
is the arity of the lambda. Lambdas are ended using the regular 0
.
Lambda variables
Lambda variables are reserved variables which can only be written to inside a lambda. Lambda variables are not overwritten after a lambda's execution, but instead before another lambda's execution, so it is possible to view arguments passed to a lambda in the global scope after the lambda has executed. Lambda variables not needed by further lambdas (because of lower arity) are not overwritten. Lambda variables have a prefixed E
to their hexadecimal variable number. So the first lambda variable is E0
, the second is E1
, etc. Regular variables cannot have hexadecimal variable numbers starting with E
, unless the hexadecimal number either is E
or has leading zeros.
Example
This code sets the variable 0
to a lambda taking three arguments (call them x
, y
, and z
) which returns x+y*z
.
208F00183022218EF0024218E10218E200C6
Golfed and compressed
Wƶ0OmYXŽð2γOá2Oâ
Comparing that to the corresponding Python code to see the golfage:
f=lambda x,y,z:x+y*z
Operators
0: Set variable (2) 1: Get/call variable (1) 2: Addition (2) 3: Subtraction (2) 4: Multiplication (2) 5: Division (2) 6: Integer division (2) 7: Modulo (2) 8: Exponentiation (2) 9: Floor (1) A: Ceiling (1) B: Equality (2) C: Inequality (2) D: Greater than (2) E: Less than (2) F: More
More operators
0: Negate (1) 1: List
Builtins
0: First element (1) 1: Last element (1) 2: Index (2) 3: Index, swapped args (2) 4: First instance (2) 5: Remove first (1) 6: First instance, swapped args (2) 7: Remove last (1) 8: Reverse (1) 9: For each (2) A: Replace (3) B: Transliterate (3) C: Split on spaces (1) D: Split on newlines (1) E: Split (2) F: More
More builtins
0: Split characters (1) 1: Join (1) 2: Join by newlines (1) 3: Join by spaces (1) 4: Integer interval (0, x] (1) 5: Integer interval [0, x] (1) 6: Integer interval [0, x) (1) 7: Integer interval (0, x) (1) 8: Sum (1) 9: Product (1) A: Reduce (2) B: Length (1) C: Binary (1) D: Hexadecimal (1) E: Base (2) F: More
Even more builtins
0: Lowercase (1) 1: Uppercase (1) 2: Match case (2) 3: Mirror (1) 4: Palindromize (1) 5: To-slice (2) 6: From-slice (2) 7: Slice (3) 8: Sort (1) 9: Swap case (1) A: Random case (1) B: Random number in (0, 1] (0) C: Random integer in (0, x] (1) D: Random integer in [0, x] (1) E: Random integer in [0, x) (1) F: More
Even even more builtins
0: Random integer in (0, x) (1) 1: Random choice (1) 2: Count (2) 3: Rotate left (1) 4: Rotate right (1) 5: Arbitrary rotation (left) (2) 6: Arbitrary rotation (right) (2) 7: Append (2) 8: Prepend (2) 9: Append, swapped args (2) A: Prepend, swapped args (2) B: Merge (2) C: Merge, swapped args (2) D: To Unicode values (1) E: From Unicode values (1) F: More
Way too many builtins
0: Unique elements (1) 1: Remove (2) 2: Remove, swapped args (2) 3: Keep (2) 4: Keep, swapped args (2) 5: Trim (2) 6: Trim whitespace (1) 7: Trim, swapped args (2) 8: Trim leading (2) 9: Trim leading whitespace (1) A: Trim leading, swapped args (2) B: Trim trailing (2) C: Trim trailing whitespace (1) D: Trim trailing, swapped args (2) E: Letters (1) F: More
Builtins everywhere
0: Digits (1) 1: Pieces (2) 2: Pieces, swapped args (2) 3: Pieces of (2) 4: Pieces of, swapped args (2) 5: Powerset (1) 6: Permutations (1) 7: Zip (2) 8: Zipwith (3) 9: Prefixes (1) A: Suffixes (1) B: Levenshtein distance (2) C: Shuffle (1) D: Mode (1) E: Unmode (1) F: More
Builtin insanity
0: Wait 1 second (0) 1: Wait (1) 2: Wait ms (1) 3: Closest (2) 4: Closest, swapped args (2) 5: To Roman numerals (1) 6: From Roman numerals (1) 7: Surround (2) 8: Surround, swapped args (2) 9: Title case (1) A: Sentence case (1) B: Unzip (1) C: Merge (3) D: Merge (4) E: Merge (5) F: More
Builtin hell
0: Merge (6) 1: Combinations (1) 2: Permutations (1) 3: Last instance (2) 4: Last instance, swapped args (2) 5: In (2)
Constants
0: 0 1: 1 2: 2 3: 3 4: 4 5: 5 6: 6 7: 7 8: 8 9: 9 A: 10 B: 11 C: 12 D: 13 E: 14 F: More
More constants
0: 15 1: 16 2: 32 3: 64 4: 128 5: 256 6: 512 7: 1024 8: 2048 9: 4096 A: 8192 B: 16384 C: 32768 D: 65536 E: 2147483648 F: More
Even more constants
0: 4294967296 1: 100 2: 1000 3: 26 4: 96 5: 36 6: "0123456789" 7: "abcdefghijklmnopqrstuvwxyz" 8: "ABCDEFGHIJKLMNOPQRSTUVWXYZ" 9: "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ" A: "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_" B: "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz" C: "zyxwvutsrqponmlkjihgfedcbaZYXWVUTSRQPONMLKJIHGFEDCBA" D: "zyxwvutsrqponmlkjihgfedcbaZYXWVUTSRQPONMLKJIHGFEDCBA9876543210_" E: "9876543210" F: More
Even even more constants
0: "zxywvutsrqponmlkjihgfedcba" 1: "ZXYWVUTSRQPONMLKJIHGFEDCBA" 2: 3.14159265358979323846 3: 2.71828182845904523536 4: "aeiou" 5: "bcdfghjklmnpqrstvwxyz" 6: " !\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~" 7: "qwertyuiopasdfghjklzxcvbnm" 8: "AEIOU" 9: "BCDFGHJKLMNPQRSTVWXYZ" A: "aeiouAEIOU" B: "bcdfghjklmnpqrstvwxyzBCDFGHJKLMNPQRSTVWXYZ"
ASCII-art
0: ASCII-art decompression (2) 1: Horizontal mirror (1) 2: Vertical mirror (1) 3: Dual mirror (1) 4: Clockwise (1) 5: Counterclockwise (1) 6: Rotational flip (1)
ASCII-art compression
Py256's ASCII-art compression uses a number and a string. The string contains the unique characters used in the ASCII-art, and the number stores the ASCII-art itself. The decompression process works by first converting the number to the base corresponding to the length of the string. Then, the digits of this new number are converted to a list of corresponding decimal values, so 123ABC
becomes [1, 2, 3, 10, 11, 12]
. Next, those numbers are indexed into the string, turning it into a list of characters. Finally, this list is joined back together to form the ASCII-art.
Example
Here is some code that outputs an ASCII-art caduceus (newlines added for clarity).
B0508C2DC119EA5AC5D9F0436F0C25A8F0CDA76B17DFF3A94ACD725B54FFCE6DA8FF3B5F0322725E 2CEFF65FF25C3FF52A515CA7FF1B18CE172C948DD446DF0E9C991FF8FF6F0DC655C654A15B474E82 165D2CD5FF46AEEA949512F0B19FFE42C2CFF8699BF0FF8A6A59DBDD6EA99FF17A29DBFF3C766FF1 BE3ECCA81AF0F0FFE77E5DBDED52BCE4F065D15C7FF7958557CF0FF9982B316F0B1FF9F08D4D7459 B9B5B8DC285E4C539C8598495F01CF089FF6D9373F0E391EF0A91E499E1AF0A2D25F0E125EEEDE7F 0FF8FF19785FFF0E75955D8D6CFF3DDE89869A533D85E4989FF3CFFA14A521318F0BFF3FFF0F0BFF EBFF18C5639FF4492C1D5B457FFE7F038FFF05F01CF026C84BBCA7B599CE6FFEDACA47F07D6638D2 9273C6F0DE845A2229DCBC49F09AC63941D66248E14FF5B9936C3D2A4AE3E49E32FFF09AF0DE7E22 FF98E95458FF748A4F0DF085CCFFA9E72D5D933FF9F0AD76F0B9C313517FFAFF17DCA6E748B6F0D3 4652DFF3F01A443AE84EB6BEAA9F016FF8291526F0DFF4FFC5DCBAF0CDAC3A11F06C3BCF0AC95217 EC5CB78CA9F0E17AAD16D3285CCC2799D7FFF0DCF0BED8C27A1E32745EB1FF12A4B977EAA54AA843 CD4C4ACFF5354C1C643B5DF0E7AFFD87D754467F0B2FF98A6D8AF0DF0295F06C4DFF22C6B8F0AA58 18D52D76E1FF2DD32F041AC61846FF5DD486B8128275781818F06BC98C1AEE5F0B26E686FF4F057E D4111A51CDFF78453754248BBC1EE1FFDA83F0DA7E9F0595955AE353AE439615CCD8F0CB528D7626 483DF011516B9534BD97E95EA44CEF0F0A28A17DDEC9741FF299EC2AE7964BE56DD6B3717CF0CF09 535DDC3915B9F0A2FFD2CA89B78FF28B86FFF01BD93C1519316E1FFF0D73FF6585764FF8E3BE5BF0 18CC76FF56F0EE5F0F02622F0AAA664D4A3FF64E18A17F01A49621F01F06B44527423B35E5FF2B43 CF013FF3ED69AA5A77F065E45B92E7AE1BD2B97EE85D36E3EF02AFFFFF09DA43BEB3F0BF0E2B82FF 5F01FF5FF69E7DE62BD5CBDA3393A6F0657B89F0159913CA4EAD98F0B11FFF01CB94475626BB29F0 D47F09747EFF26D38117368C68F0DCB1F0B2FFF0F05181E2DEE822119E3B8AFF4AF039828CA5DF0F 05587A23BB394EA69947365B6FF3FFFF27299FF56E1DFFCC66F0AF0AB4AFFE4F05EDFFB77F06C18D 2C56F0A9CAA1F01DFFFF6627CEFFBDFF619EF05B6FFE56BB663F01BF073147699ADA7DF029F0475C 2FFDF042AF0327431992F05A7DF0EEDE6B6F0DF0893FF3F0713FFD7B44EF02FF7822B9FF8B2AF05B 85133FF99AEDF0738FF2DFFFFCCCB479D36C6EA2A9437F0EC69AE2379FFFF4FFB6588E14797BF0F0 729279BEADACBFFCAFF7F0A2825A595CFF545F0A554DD76F07EFFAC81D4B331ACC66AFF4EFF6F078 F039C2D5B76C43D19598F07DCC7889A5E58FF8F0D9F031547C8BD5556A9B66863E267FFCF07FFBA7 39CCC3F0BAEF0F098D4E4EFFD4BE333867F07FFC36E91F006642F03862F0A5FF2C2E2D22276F02FF 595F05C573B6594613D7C0C6
Golfed and compressed
B58ÂÜHž¥¬₆Ÿ4sðÂ₃ƶCÚ\±}ÿw”¬×bµΔüæÚƶóµðodbâÎÿ'ÿbÃÿΣ¥LÊƵñ±Œá>ÉвÝε/ðéÉ‘ÿƶöðÜ'₅'мL´@è X'ÒÍ!ô,î©иιlBPÿäiiÿ†™¿Fø¦¥ć½Öê™ÿN¢ć¿óÇ(ÿRãìÊΛ¯FFþ]åÛÞÕhÎΔ6₆LÇÿ_₁∊|ðÿ™‚³Mð±ÿŸ8Ô×ζ ››₄ĆÂ…äÅvÈ₂„•ðSð‰ÿ/“?ðã‘ïA‘ä™á¯Ajbðábîíçðÿƶñ—…ÿðç₂∊ØÖÏóÝè˜+¥pØ и‰ÿyÿ¡мΣJOð¿óÿðð¿ þ¿ñŒ∍vÿε’ÁÕ´∞ÿçðuÿð!1Ï2.„»Ê{₂œæÿí¬¤Ƶ7Ö%Ćfdy;Dèζ¢YćËÄŸ9¬%”T(aŽKÿ₄™sÃÒ¤®ǝиãlÿ9¯Dçâ lùŽ•ζƶ÷в¤ðß8₅Ïúž>ÕÙpÿŸA×;BœnrNÿ¯ñ}Ê:@‹;Dq'jÿʒ1¤δ®„ë-ê©ðMÿ‚‘Σ;DÿΔü₆˯CÚáV6üð¬•X ~ÅË^ÊŸENªÑ/o…ÌÂ_ćƵÿDÏBíŒd¡ãdζëVñgн—~ª≠ª„yÔĬÿΩ≠ÁÆδµßE`ÿØ}[ε)ð²ÿ˜¦Ø¯Dðf!6Äßòi-ƶA¥ ΛĆΣ×:VòÝoðβ¬#„;õÝв-Λed∞ΛΛƶ6¼˜Á®åð²:*;ôð∞íβH¥Sß÷„Ω[γв»ÁîVý¨ʒD§éð₂₂∊®rwäv#₅ÍƶCµe×$ &ƒß1LM¹ΩнÙ~•êεÎðð¢ŠNÝì—βÿfžÂ®_&¾∍Ý-tNÏCð•rÝÑ₄ŸAlýi¨›^ÿe¸;ÿ1½“Áι“Máÿð×ʒö₁∞&ÿŽxå¿ 1ŒÇ;õ;EåððcYðª¦&Ô£ÿ&áŠNðQи$V1ð-εΣ@Z³ !ò´yðJÿǝÖš¥§Ƶ6 ζ¹k`á½h—î…Ó:ǝðgÿÿðć¤xëʒBðâ¸l õðVõÿ+çÞ$½₅½£vw;6∞¸Ÿ1₂‘y¤êÙƶBHÿðS¹ε[$-²ŸDθð—θïò/uH?*ÆƶDËVBlÿF5OUjî‚XP㸯ô¯3˜eÊ₆ð ð∊‡¢x³”ê+”?'¶ÿʒÿò>™ÿ∍áßüÆ;Að«мÿäð ßû]ð.OÒÅ;AœªV1ßÿö$|ïûßöPï5¶ÿå-¶%ðRð?K\™λ§ß2Ÿ4[ Âÿß4gðo@n™l5§ßEíæ¶ðß8“ÿʒ7Jÿ×´Γðl÷‚hŸø²¯5¸ιpÿ™®ß7uÿjÿÿÌËθćsÆêg”tðì+®Z_ÿÿΔû'ˆáθ—¿F 7fd›êÚËÿÊÿƵAeb¥•Ïõζð¥≠Ý\ð~ÿ¬ΛÔ³n¬Æ,ÿΓÿ;7ƶ3œj₄\ÄzP₂ƶ7ÜLjš ₁ÿƶDŸ3LθȽ∊∍©¶*%â)ÿÏ7ÿº ?œÌʒB®ðð˜Ôäïýнãp†Ƶ7ÿÃ:‘ð6&l3†lA!òÂâÒY\ðlõ•ð₅∞x'”#z|
Output
d888b __,.---"""-. 8888888 .-"""---.,__ _.-' ._._._._,_ `"-. 8888888 .-"` _,_._._._. '-._ ,__.-' _/_/_/_/_/_/_/_/_,_`'. Y888P .'`_,_\_\_\_\_\_\_\_\_'-.__, `'-._/_/_/_/_/_/_/_/_/_/_/,_`"._ dWb _."`_,_\_\_\_\_\_\_\_\_\_\_.-'` '-;-/_/_/_/_/_/_/_/_/_.--. WWWWW .;;,_\_\_\_\_\_\_\_\_\-;-' /_/_/_/_/_/_/_/_// e \IIIII;;a;;;\_\_\_\_\_\_\_\_\ '-/_/_/_/_/_/ / ,-'IIIII'=;;;;; \_\_\_\_\_\-' /_/_/_/_ / / 88888 ;;;;; _\_\_\_\ '-/_/| | 88888 ;;;;;\_\-' \ \ 88888 ;;;;; '. '.'888'.;;;;' '. '888;;;;' '. .;;;;' .;;;;'. .;;;;8. '. .;;;;'888'. '. .;;;; 888 \ \ ;;;; 888 | | ';;;; 888 / / ';;;;.888.' .' ';;;;8' .' ';' .' .' .;;;. / /8\;;;; / /888;;;;, | |888 ;;;; \ \888;;;;' '. '8;;;;' '.;;;;' ;;;;` \ ;;;;8| | ';;;8/ / '-'8'-' 8
String literals
String literals are started by 6
and ended by 0
. As usual, 0
s and F
s are prepended with F
s. The hexadecimal digits in the literal correspond to UTF-8 bytes. An easy way of getting the literal you want is to simply enter the hex bytes visible from an xxd
of the text (properly escaped, of course).
Example
Here's a simple Hello, World!
program.
B0648656C6C6FF2C2F0576FF726C64210C6
Golfed and compressed
°&†∍ÆÆÿil5\ÿ>.&X
Python comparison:
print('Hello, World!')
Dictionary compression
Py256 comes with a built-in dictionary. This dictionary is identical to 05AB1E's. Similar to 05AB1E, elements in the dictionary are referred to by their index. Dictionary literals are started by 7
and ended by 0
. Once again escaping applies. Each dictionary word is encoded as its 0-based index in the dictionary, with the number left-padded with zeros to length 4
. Spaces are automatically added between words in a single dictionary string.
Example
Once again a Hello, World!
program, but this time using the dictionary.
B03FFFFFFD3FFFFFF972419062C2F003FFFFFF97F011806210C6
...sadly much longer than pure compression.
Golfed and compressed
B3ÿÿÿÓÿÿÿ—aP6il0ʒÿÿùƵ1O6X
Numeric literals
String literals are started by 8
. As usual, they are ended by 0
and escaping applies. Not much to say here, just a hexadecimal integer.
Example
Output the answer to life, the universe, and everything.
B082A0C6
Golfed and compressed
B8g
Python comparison:
print(42)
HTTP
0: Request (1) 1: Server (1)
HTTP server
The HTTP request is pretty simple; just send a request to the URL and return the response content. But the HTTP server is a bit more complicated. It first hosts an HTTP server on port 80
. Next, it waits for a request. When it receives a request, it sets the lambda variable E0
to the request URL followed by a space and the requester's IP address. For example, if 1.2.3.4
sent a request to http://www.mycoolwebserver.com/bush
, E0
would get set to /bush 1.2.3.4
. Next, the Py256 code passed as an argument is evaluated. If this evaluated text starts with HTTP
, it will treat the result as a raw HTTP response. Otherwise, it will respond with an HTML file containing the evaluated content.
Example
Return 418 I'm a teapot
for each and every HTTP request made to your computer.
9164854545F02FF312E312F0343138F0DF0A00C6
Golfed and compressed
‘&…ζζðlóIãIðqnuðßA
I/O
0: Output (1) 1: Output, no newline (1) 2: Input all (0) 3: Input line (0) 4: Input char (0)
Statements and conditionals
0: If (2) 1: While (2) 2: Until (2) 3: Else (1) 4: For (2) 5: Break (0) 6: Terminate (0)
All loops automatically set the lambda variable E0
to the current 0-based index each iteration.
Advanced operators
0: Prime test (1) 1: Arbitrary prime (1) 2: Factorial (1) 3: AND (2) 4: OR (2) 5: XOR (2) 6: NAND (2) 7: NOR (2) 8: XNOR (2) 9: NOT (1) A: Bitwise AND (2) B: Bitwise OR (2) C: Bitwise XOR (2) D: Bitwise NAND (2) E: Bitwise NOR (2) F: More
More advanced operators
0: Bitwise XNOR (2) 1: One's complement (1) 2: Square (1) 3: Cube (1) 4: Hypercube (1) 5: Square root (1) 6: Cube root (1) 7: Hypercube root (1) 8: Reciprocal (1) 9: Increment (1) A: Decrement (1) B: Halve (1) C: Double (1) D: Third (1) E: Triple (1) F: More
Even more advanced operators
0: Quarter (1) 1: Quadruple (1) 2: Greater than or equal to (2) 3: Less than or equal to (2) 4: nCk (2) 5: nPk (2) 6: Power of 2 (1) 7: Power of 10 (1) 8: GCD (2) 9: LCM (2) A: Even (1) B: Odd (1) C: Double increment (1) D: Double decrement (2) E: Divisible (2) F: More
Even even more advanced operators
0: Divisors (1) 1: Proper divisors (1) 2: Cartesian product (1) 3: Cartesian product (2) 4: Cartesian product (3) 5: Unique prime factors (1) 6: Prime factors (1) 7: Prime factor powers (1) 8: Ln (1) 9: Log (1) A: Log2 (1) B: Arbitrary log (2) C: Sign (1) D: Reduce left (2) E: Reduce right (2) F: More
Way too many advanced operators
0: Cumulative reduce left (2) 1: Cumulative reduce right (2) 2: Enumerate (1) 3: Swapped enumerate (1) 4: Enumerate (2) 5: Swapped enumerate (2) 6: Enumerate, swapped args (2) 7: Swapped enumerate, swapped args (2) 8: Reversed enumerate (1) 9: Swapped reversed enumerate (1) A: Reversed enumerate (2) B: Swapped reversed enumerate (2) C: Reversed enumerate, swapped args (2) D: Swapped reversed enumerate, swapped args (2) E: Greedy closest prime (1) F: More
Advanced operators everywhere
0: Lazy closest prime (1) 1: Non-unique closest prime (1) 2: Previous prime (1) 3: Non-unique previous prime (1) 4: Next prime (1) 5: Non-unique next prime (1) 6: Pascal addition (1) 7: Pascal subtraction (1) 8: Reversed Pascal subtraction (1) 9: Pascal multiplication (1) A: Pascal division (1) B: Reversed Pascal division (1) C: Pascal integer division (1) D: Reversed Pascal integer division (1) E: Pascal reduction (2) F: Reversed Pascal reduction (2)
Examples
Hello, World!
°&†∍ÆÆÿil5\ÿ>.&X
Cat
°²
Truth-machine
°±W€²ÁX€±Λ
Reverse cat
°u²
Adder
°Y³³
Primality tester
°Ð²
Infinite loop
Áβ
Screamer
CKRMβ
Interpreter
No interpreter as of right now, if someone could make one that would be greatly appreciated :)
Generator
Only compressed Py256 programs are valid. An 05AB1E program to convert from hex Py256 (Py16?) to compressed Py256 can be found at Try it Online.