Branch

From Esolang
Jump to navigation Jump to search
Not to be confused with Branch (Johnki).

Branch is an esoteric programming language created by User:HyperNeutrino in 2021. It is a Turing tarpit that operates on a binary tree as its memory structure. Its source code is available under the MIT License here. You can also try it online with the online Branch interpreter.

Description

Branch has 95 valid instructions, from codepoint 33 (!) to 127 (~). All other characters are ignored. Command line arguments are loaded into the memory by default along the left branch of the tree. Finally, -m can be specified first with two numerical arguments to limit the maximum size of the tree and of the output.

Tutorial

Branch operates on a binary tree of long long ints, which is a tree where each node has two children. If there are command line arguments, the first argument is stored at the root of the tree, and each subsequent value is stored in the left child of the value before it. Otherwise, the memory starts as a single node containing 0.

Instructions

Branch has 26 registers, 13 of which store a data pointer, and 13 of which store a number. A-M will set one of the registers to the current position. a-m will move the data pointer to the stored location, unless the register was never set, in which case nothing happens. Register A is initially set to the first node, and as long as no register has been manually set, the first up to 12 nodes that are created by any means will be stored in the next available register from B-M. N-Z will set one of the registers to the current value, and n-z will set the current value to the stored data, unless the register was never initialized, in which case nothing happens. The first up to 13 command line arguments are stored in N-Z to begin with.

The following is a complete list of instructions. Initially, the instruction pointer is at 0, and it moves forward by 1 each time, unless that is changed by square brackets ([...]), which function as a looping mechanism. By default, when a node is created, its value will be initialized to zero. The exception is binary operators (which operate on their left and right children and set the current node's value to the result), which read the values from STDIN if more nodes are needed (the left node is created and read to first if both are missing).

Instructions
Command Description
! Logical NOT; set the current value to 1 if it is 0, and 0 otherwise
" Copy the current value to its parent (creates the parent with this as the left child if needed)
# Output the current value as a number
$ Read a number to the current value
% Modulo; returns 0 if the right argument is 0
& Bitwise AND
' Exponentiate
( Delete the current node (and therefore all of its descendants). If it has a parent, go there. If this is the root, create a new tree with value 0
) End the program
* Multiplication
+ Addition
, Read a character and set the current value to its codepoint
- Subtraction
. Output the current value as a character by codepoint (doesn't work well for values outside of the printable ASCII range)
/ Move to the left child (if absent, sets it to 0)
[0-9]+ Set the current value to a number
: Division; returns 0 if the right argument is 0
; Copy the parent's value to the current value; if absent, creates a parent and sets its value to 0 and its left child to the current node
< Less Than; 1 if the left argument is strictly less than the right argument and 0 otherwise
= Equal To; 1 if the left argument is equal to the right argument and 0 otherwise
> Greater Than; 1 if the left argument is structly greater than the right argument and 0 otherwise
? Conditional Branch; go to the left child if the current argument is 0 and the right child otherwise; if the child is absent, create it and set it to 0
@ Push the current instruction pointer to the IP stack, then jump back to the start of the program.
[ Loop Start; if the current value is 0, jump to the matching Loop End
\ Move to the right child (if absent, set it to 0)
] Loop End; if the current value is not 0, jump to the matching Loop Start
^ Move to the parent (if absent, set it to 0, and the current node becomes the parent's left child
_ Negate
` 2-byte built-ins (get a full list on the Branch wiki on GitHub)
{ Decrement
(pipe) Bitwise OR
} Increment
~ Pop the top of the IP stack and restore the instruction pointer to that location. If the IP stack is empty, this doesn't do anything.

Sample Code

Hello World

72.101.108Z..111O.44.32.87.o.114.z.100.33.

Try it here!

Fairly straightforward; load every value as a number and then print it as a character, using registers in some places to save bytes.

Add two numbers

+#

Try it here!

The + operator creates its children nodes and reads their data from STDIN, and then # outputs the value.

Fibonacci (Infinite Sequence)

1XY[/x#^\yX^+Y10.]

Try it here!

Using registers, X and Y are initially set to 1, then each time, X and Y are loaded as the children, X is set to the value of Y, and Y is set to the sum of the previous value of X and Y. Note that because Branch is implemented in C and uses long long int, the values quickly overflow and become garbage.

Fizz Buzz

\^//C//70/105/122Z/zc\/66/117/z/za1O[/ob3^%Vc/v?[./]b5^%Wc\w?[./]a/vbw^*/0bo^?[#0]a10.o}O/;b101^-]

Try it here!

This outputs up to 100. Loads "Fizz" and "Buzz" into two branches, then at each step, modulo and use conditional to determine whether or not to output each of "Fizz" and "Buzz". Finally, if neither remainder was zero, output the number itself instead.