Symesol
Introduction
Symesol, short for SYMbol ESOteric Language, is an esoteric programming language by Abraham Karplus. Its most striking feature is using symbols for variable names and letters for operations. It is Turing complete. Symesol is generally easier to program in than to read, particularly if variable names are deliberately chosen to mislead. I am currently working on a Symesol compiler in Python. Symesol files have the extension sye. Compiled (Python) files have the extension syx. All errors are fatal. It is also a fatal error to have any not understood characters (e.g. capital letters or non-ASCII characters).
Variables
Types
There are three types of variables: reals (with subtype integers), functions, and arrays. Arrays can contain any of the types, even subarrays. It is an error to treat any type as another type. Reals do not need to be explicitly declared before use, but arrays must be initialized with the y operation (see "Basic Operations" below). Defining and using functions requires special syntax (see "Functions" below).
Names
Variable names are formed from the characters !"#$%&'()*+,-./:;<=>?@[\]^_`{|}~ combined in any order, as alphanumerics would be in most programming languages. It is conventional for the first character of a variable name to reflect something about the variable: : for functions, $ for parameters, # for arrays, ~ for loop indices, % for representations of characters, ? for booleans (integers 0 and 1), = for results of comparison, . for included content, _ for hidden variables in included files, and ` for highly temporary variables.
Literals
The only type of allowed literal is the integer, which is written in base 10 with the digits 0123456789 as normal. There is no way of representing a negative or non-integer number as a literal, but an integer stored in a variable can be modified to a non-integer with the arithmetic operations (see "Basic Operations" below).
Characters and Strings
Characters are represented as integers using the Unicode codepoints. String can be done as arrays of these integers, though output is only single character at a time. As per ASCII, end-of-file has value 4, and newline has value 10.
Comments
A comment is begun at any point with the space character, and continues until terminated by the newline character. Any characters other than newline may safely appear within the comment. The newline character has only one other use (see "Includes" below), and so may safely be used as a separator.
Includes
Another Symesol file may be included into the current one with the q syntax. After the q, all characters until a newline are treated as the name as the file to include. Included code is inserted at compile time.
Basic Operations
All variable names used in this section are placeholders. The ! and ~ placeholders used in this section may be replaced by literals, but all others must be actual variables.
Arithmetic
- a add
a!a@
Increases the real in @ by the real !.
- m multiply
m!m@
Multiplies the real in @ by the real !.
- n negate
n@
Negates (multiplies by negative one) the real in @.
- v inverse
v@
Takes the multiplicative inverse (one over) of the real in @.
Communication
- i input
i@
Stores the Unicode value of the next inputted character in @.
- o output
o!
Prints out the character corresponding to the Unicode value !.
Arrays
Arrays have a fixed length set at array initialization that cannot be changed. Attempting to read or write outside this range is an error. Reading a value in an array if that value has not yet been written is an error. Array indices go from 0 to the length of the array minus 1.
- h length
h#h@
Stores the length of array # in the real @.
- r read
r#r~r@
Stores the value at position ~ of array # in @.
- w write
w!w~w#
Stores the value ! in position ~ of array #.
- y initialize
y!y#
Defines the variable # to be an array of length !. Any former value in the variable # is overwritten.
Miscellaneous
- c compare
c!c=
Stores the result of the comparison between ! and = in =. The result is 1 if ! is larger, 0 if they are equal, and -1 if = is larger.
- j not
j@
Stores 0 in @ if it is non-zero, 1 otherwise.
- s store
s!s@
Stores the value of ! in the variable @. This will copy the value, even for arrays.
- x return
x!
Returns the value ! from the function. See "Functions" below. If doubled to xx, exits the program.
Control Flow
The variable ? is here a placeholder.
Conditionals
A conditional, or "if-statement", has the format f?t[body]z. If the real ? is true (non-zero), the body is executed. Otherwise, the entire conditional is skipped.
Loops
A loop has the form l[body]z. The body is repeatedly executed until a break statement b, usually inside a conditional, is encountered, at which point the loop exits. A loop inside a function will also stop if the function returns from inside the loop.
Functions
The variable names in this section are placeholders.
Define
The define statement d has the format d:[parameters][locals]g[body]z. The variable name : is the name of the function. Parameters are zero or more statements of the form p$, specifying an argument to the function referenced internally as e.g. $. The body of the function is run whenever the function is called. The return operation x must be used because it is an error to encounter the end of the function while executing it. Functions are defined at run time. Any variables referenced in the function that are not parameters or defined in the function are evaluated at definition time.
Use
A function : is called using the use statement u. It has the format u:u@[parameters], where : is the name of the function, @ is where its return value should be stored, and parameters is zero or more (depending on how many arguments the function takes) statements of the form p$, where $ is a value to pass to the function. All arguments are pass-by-value.
Examples
The variable names in this section are not placeholders.
Copies input to output
li%s4s`?c%c`?j`?f`?tbzo%z
Copies input to output, incrementing character values by 1
li%s4s`?c%c`?j`?f`?tbza1a%o%z
Copies input (max 1000 chars.) into an array then outputs the array
s1000s+s0s~[s0s~]y+y# ls+s`=c~[c`=j`=f`=tbzi%s4s`?c%c`?j`?f`?tbzw%w~[w#a1a~[z ls+s`=c~]c`=j`=f`=tbzr#r~]r%o%a1a~]z
Prints "Hello world!" followed by a newline
o72o101o108o108o111o44o32o119o111o114o108o100o33o10
Defines a function to check for EOF and uses it in copying input to output
d:}p$%gc4c$%j$%x$%z li%u:}u?u%f?tbzo%z