Backhand
Backhand is an esoteric programming language created by User:Jo King which is a 1D stack based language inspired by 2D languages like ><> and Befunge. The name comes from the phrase "Back and Forth", which describes the way the instruction pointer travels.
Concepts
Backhand operates on a 1D tape of instructions, but crucially it does not execute these sequentially. Instead, the instruction pointer moves multiple steps at a time, initially starting at the first instruction, and moving in steps of 3. For example, the program:
1 1 + O @
will skip all the spaces between instructions and only executes 11+O@
(which simply adds 1 to 1 and outputs the result). When the instruction is about to step out of bounds of the program, it instead reverses direction and moves the other way. For example, the above program can be shortened to 1O+1@
, which executes as below.
1..1. Bounce off end and go left ..+.. Bounce off start and go right .O..@ End
It's easy to confirm this by counting the number of dots between each instruction, which should be 2 (ends are only counted once)
This can lead to compressed programs folding in on themselves, such as "ol!,ld elWHro"
, which prints "Hello, World!". You can also decrease and increase this step counter itself, using instructions like ^
or M
to increase it, or v
and W
to decrease it. Note that if you decrease the step counter below zero than directionals like <
or >
will have the opposite effect.
Data structure
Similar to Brain-Flak, Backhand uses two separate stacks of numbers. You usually operate on the main stack, but you can push/pull to the other stack with (
and )
respectively, or even swap the two stacks with x
. Attempting to pop from an empty stack will yield 0
instead. Backhand also has a register, which can store one value to be retrieved later (both with the &
instruction).
Input/Output
Input can be read with the i
and I
instructions, which reads characters and numbers respectively. The i
instruction pushes the ordinal value of the next character of input, and I
ignores input until it reaches a number (which can include a negative sign before it). For both instructions, if no more input is available they push -1
to the stack.
There are also the associated output instructions o
and O
which output as characters and numbers respectively.
Errors
Errors are caused by:
- Division by zero
- An empty program
- Trying to print a value out of the range of
0
to0x10FFFF
Instructions
Any character that is not an instruction is a no-op and does nothing.
Literals
Character(s) | Name | Action |
---|---|---|
0-9a-f |
Number | Pushs the appropriate number. The characters a to f push the values 10 to 15
|
" |
String | Turn on string mode, which pushes the ASCII value of each character until it reaches either another "
|
' |
Character | Push the ordinal value of the next instruction instead of executing it |
Stack manipulation
Character | Name | Action |
---|---|---|
~ |
Pop | Pop and discard a
|
$ |
Swap | Pop a then b and push a then b
|
: |
Dupe | Pop a then push a twice
|
& |
Register | If there is not a value in the register, pop a and store a in the register. Otherwise, push the value in the register and clear it
|
r |
Reverse | Reverse the stack |
l |
Length | Push the length of the stack |
( |
Pull | Pop a from the other stack and push a
|
) |
Push | Pop a and push a to the other stack
|
x |
Switch | Swap the main and other stack |
Control Flow
Character | Name | Action |
---|---|---|
< |
Left | Change direction to left |
> |
Right | Change direction to right |
{ |
Step Left | Step left one |
} |
Step Right | Step right one |
^ |
Increment Step | Increase the step value by 1 |
M |
Double Increment Step | Increase the step value by 2 |
v |
Decrement Step | Decrease the step value by 1 |
W |
Double Decrement Step | Decrease the step value by 2 |
? |
Random | Step left or right randomly |
j |
Jump | Pop a and jump to the a th character, bouncing off the sides as usual. 0 represents the first character
|
s |
Skip | Pop a and skip forward a characters, bouncing off the sides as usual. This moves forward in the current direction
|
@ |
Terminate | End the program |
Branching
Character | Name | Action |
---|---|---|
_ |
Decision Step | Pop a and if a is zero step right, else step left
|
Decision Change | Pop a and if a is not zero reverse direction
| |
! |
Not | Pop a and push 1 if a is equal to 0 , otherwise 0
|
L |
Less | Pop a then b and push 1 if a is less than b , otherwise 0
|
G |
Greater | Pop a then b and push 1 if a is greater than b , otherwise 0
|
E |
Equal | Pop a then b and push 1 if a is equal to b , otherwise 0
|
Arithmetic
Character | Name | Action |
---|---|---|
- |
Subtraction | Pop two values a then b and push b-a
|
+ |
Addition | Pop two values a then b and push b-a
|
* |
Multiplication | Pop two values a then b and push b*a
|
/ |
Division | Pop two values a then b and push b//a , the integer division of b and a
|
% |
Modulo | Pop two values a then b and push b%a , where the sign of the result matches the sign of a
|
[ |
Decrement | Pop a and push a-1
|
] |
Increment | Pop a and push a+1
|
Input/Output
Character | Name | Action |
---|---|---|
i |
ASCII input | Push the next byte of input |
o |
ASCII output | Pop a and output a as ASCII
|
I |
Number input | Ignore input data until it reaches a number and push that number. If the number is preceeded by a - then the number is negative.
|
O |
Number output | Pop a and print a as a number
|
\n |
Newline | Print a newline |
H |
Halt | Print the contents of the stack as a string and terminate the program |
h |
Finish | Output the top of stack as a number and terminate the program |
Example Programs
Cat program
Terminates with an error:
io
Or terminating safely:
{i: o]@|{
Hello World!
"ol!,ld elWHro"
Factorial
1@ IO :~!{|{}: ([ *).
Truth Machine
I|@}: O
Quine
"#v{<@^:[ba+0v|{$:o[}
External Resources
- Backhand Interpreter
- https://tio.run/#backhand, an online interpreter