From Esolang
Jump to navigation Jump to search
I'm tired of all these motherfucking operators in all these motherfucking fixities!

Real Introduction

Sorry about that above, I just couldn't resist.

ADDI is a language that consists entirely of operator expressions to form its program. It is, really, just a series of semicolon-separated expressions that somehow form a program, maybe even a TC language. It was designed to be a different, but believable, language; one that could've arisen and come into common use in some other world.


Note that whitespace is entirely ignored.

digit     ::= "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9" ;
bool      ::= "True" | "False" ;
num       ::= digit {digit} ["." digit {digit}] ;
str       ::= '"' ?escaped-string? '"';
name      ::= /[a-zA-Z_][a-zA-Z0-9_]*/ ;
op        ::= {!name & !num} ;

parenexp  ::= "(" exp ")" ;

tuple     ::= "(" [exp {exp ","}] ")" ;
list      ::= "[" [exp {exp ","}] "]" ;
set       ::= "{" [exp {exp ","}] "}" ;

container ::= tuple | list | set ;

exp       ::= parenexp | container | exp op exp | op exp | exp op | bool | num | name | {op} ;

line      ::= exp ";";

program   ::= {line}


An ADDI program consists of a number of lines separated by semicolons. Each line is an expression, with operators going left-to-right with no order of operations, except that parenthesized things go first. Operators can be prefix, postfix, infix, or nofix (nofix operators can be side-by-side, but must be enclosed in parentheses (even if alone)), with operators potentially having different meanings in different fixities. Expression operands are either variable names or (decimal) numbers, or they can be tuples, lists, or sets of the same.

Data Model

Because I like this data model so much, ADDI uses an infinite registry of Deques with an optional reader head for location and a single scalar accumulator. Deques can be of infinite length. Deques and the accumulator can hold various types of data: strings, integers, floats, arrays, other deques, or objects.


There are a lot of operators. Like, Unicode levels of operator. If there aren't as many operators as I'm leading you to believe, then I just haven't added them all yet.


Unless otherwise noted, Nofix operators return null.

Operator Name Meaning Before After
! NOT POP a value and PUSH its logical inverse a... (!a)...
$ POP POP a value and return it ab... b...
% MOD Pop a, pop b, push b%a ab... (b%a)...
& AND Pop two values and push their bitwise ANDing ab... (b&a)...
* MULT Pop two values and push their product ab... (b*a)...
+ ADD Pop two values and push their sum ab... (b+a)...
- NEGATE Pop a value and push its negation a... (-a)...
/ DIV Pop a, pop b, push b/a ab... (b/a)...
: DUP Duplicate the value on the top of the deque a... aa...
< LESSER Pop two values, push the lesser 37... 37...
= EQ Pop two values and, if they're equal, push their value aa... a...
> GREATER Pop a, pop b, push the greatest one. if 37... 7...
? INPUT Get a character of input and push it on the stack
@ STRIP Pop values from the stack until one is not zero, then push it back on 000a... a...
\ SWAP Pop two values from the stack and push them in opposing order ab... ba...
^ XOR Pop two values and push their bitwise xor ab... (b^a)...
_ DECCUMULATE Drop a value from the accumulator b...; a ab...; a
` ACCUMULATE Pop a value into the accumulator ab...; 0 b...; a
| OR Pop two values and push their bitwise ORing ab... (b|a)...
~ BITWISE NOT Pop a value and push its one's compliment a... (~a)...


Operator Type Name Meaning Before After
! * PUSH Push a value onto the current deque
& int REF Reference the deque at the given index &5 (reference to deque #5)
* ref DEREF Return a clone of a referenced object *&5 (clone of deque #5)
+ * IDENTITY Return the selected object +5 5


Operator Type Name Meaning Before After
@ * REDUCE Evaluate the previous argument until it fails


Operator Type Name Meaning Before After
! iterable, int INDEX Get the item at a given index from a list [1, 2, 3]!1 2
int, int GETBIT Get the bit at the given index (from the end, modulo 64) 42!3 True
$ iterable, int DROP Drop the item at the given index [1, 2, 3]$1 [1, 3]
int, int TOGGLE Toggle the bit at the given index (from the end, modulo 64) 42$3 34
& *, * ATOMIZE Save the program state, evaluate its first argument, if it succeeds evaluate its second, if it succeeds return True. If either fail, revert state and fail (!5)+(!0)+((/)&(!0)) Failure (5/0 fails)
* *, int COPY Generate a list with n copies of m 6*3 [6, 6, 6]
+ *, * CONCAT Evaluates both of its arguments in order.
/ *, * BACKUP Evaluate its first argument, if it fails evaluate its second argument, fail if the second fails, else return the one that succeeded (!5)+(!0)+ ((/)/(*)) 0
: num, num RANGE Create a set from the numbers in a range (excluding the last one) 0:3 {0, 1, 2}
< iterable, * APPEND Add a value to the end of a list/set/etc. [0, 1, 2]<3 [0, 1, 2, 3]
= name, * ASSIGN Assign a name to a value, return that value x=0 0
> *, iterable PREPEND Add a value to the beginning of a list/set/etc. 3>[0, 1, 2] [3, 0, 1, 2]
? ~bool, * EVAL-IF Evaluates its second operand if its first evaluates to TRUE (and return its value, else null)
@ ~bool, * EVAL- WHILE Evaluates its second operand while its first returns TRUE (and return a list of return values)
\ iterable, iterable[int] ROT Rotate the elements of its first arg by their indexes in its second arg [1, 2, 3, 4]\ [1, 3] [1, 4, 3, 1]
| *, * ALT Either a or b (creates a set of a and b) 1|2 {1, 2}

Special Variables

Some names are special. They have unique meanings that other variables do not have. These are:

  • out: A list that has all new items printed from it at the end of each cycle

Example Programs

Hello World

out < "Hello, World!";


True @ ((?)+(out<($)));