We are currently working on new rules for what content should and shouldn't be allowed on this website, and are looking for feedback! See Esolang:2026 topicality proposal to view and give feedback on the current draft.
PyStacky
| Designed by | User:NTMDev |
|---|---|
| Appeared in | 2026 |
| Memory system | Stack based |
| Dimensions | One Dimensional |
| Computational class | Turing complete |
| Reference implementation | Implementation |
| Influenced by | Python |
| File extension(s) | .txt |
- This is still a work in progress. It may be changed in the future.
This wiki is consistent with the most recent github commit
Introduction
PyStacky, or Stacky, is an esoteric stack-based language built on Python 3.13. It contains a custom user interface for viewing the global and local stacks during execution, and also local variables.
The github repo, where all download and other more technical information is here
Please report any issues in the issue tracker on github rather in this wiki. This wiki is a documentation for PyStacky, not the issue tracker.
User Interface
After the compiler has successfully parsed and compiled the program, a tkinter widget window will open. The main widget UI has 5 buttons: Run, Step, Reset, Rerun, and Reload.
Run
This button simply runs the program, stepping through the program at 5ms per instruction. Also, this button changes to Pause when the code is running, so you can pause the program while it is running
Step
Step through exactly one instruction per press
Reset
Stop the program and go back to the very start of execution
Rerun
Reruns the program. This feature actually instantly progresses through all instruction steps
Reload
Reload the currently loaded file to apply any changes made to the file. If there were no differences between the refreshes, the console will send out a warning
Loading Code
To load and execute a PyStacky program, you must first create a .txt file in the scripts directory. It should be in the main zip file you downloaded from github. To test that the compiler is working, enter example as the file name upon execution of the compiler (PyStacky.py). It should output a string, namely "Hello, I am a function!".
Comments
To create a comment, use //
Instructions
PyStacky has a fairly small instruction set, with only 14 distinct instructions. Any other functions have been written in Python and directly interact with the internal stack (called native functions), through Natives._push and Natives._pop.
Documentation Structure
Structure: The arguments this instruction takes, and their definition
Functions: What the instruction(s) do
... Additional Information Here ...
Push and PushLocal
Instruction: push, pushlocal
Structure:
| Arguments | Definition |
|---|---|
Value |
Any valid PyStacky value |
Functions:
| Function | Usage |
|---|---|
Push |
Pushes Value to the global stack
|
PushLocal |
Pushes Value to the local stack
|
Note: The Push function has two different styles, a global and local style.
Pop and PopLocal
Instruction: pop, poplocal
Structure:
| Arguments | Definition |
|---|---|
VariableOptional |
Predefined variable that can be accessed at the scope the instruction can access. This argument is optional. |
Functions:
| Function | Usage |
|---|---|
Pop |
Pops a value off of the global stack, optionally into a variable. If the VariableOptional argument is not set, discards the value.
|
PopLocal |
Pops a value off of the local stack, optionally into a variable. If the VariableOptional argument is not set, discards the value.
|
Note: The Pop function has two different styles, a global and local style.
Define and DefineGlobal
Instruction: define, defineglobal
Structure:
| Arguments | Definition |
|---|---|
Name |
Name for the variable |
Value |
Any valid PyStacky value |
Functions:
| Function | Usage |
|---|---|
Define |
Defines a new variable in the local scope, if it does not exist yet
|
DefineGlobal |
Defines a new variable in the global scope
|
Note: The Define function has two different styles, a global and local style.
Set and SetGlobal
Instruction: set, setglobal
Structure:
| Arguments | Definition |
|---|---|
Name |
Name of the variable |
Value |
Any valid PyStacky value |
Functions:
| Function | Usage |
|---|---|
Set |
Sets the value of the variable Name to Value in the scope, if it exists in the local stack
|
SetGlobal |
Sets the value of the variable Name to Value in the scope, if it exists in the global scope
|
Note: The Set function has two different styles, a global and local style.
Call
Instruction: call
Not to be confused with CallNative and CallLocalNative
Structure:
| Arguments | Definition |
|---|---|
FunctionReference |
Name or variable of the function to be called |
{Arguments...} |
Many values; as many as you need to be able to fulfill every argument of the FunctionName function
|
Function:
| Function | Usage |
|---|---|
Call |
Calls the function. The instruction will immediately step to the function called, and returns back to the caller function when the function reaches the end of the function with End, or is terminated with Exit
|
End
Instruction: end
Structure:
| Arguments | Definition |
|---|---|
N/A |
This instruction does not require arguments |
Function:
| Function | Usage |
|---|---|
End |
An instruction to indicate the end of an If-Elif-Else, Loop, or Function statement. This is necessary to avoid a SyntaxError from the compiler
|
CallNative and CallLocalNative
Instruction: callnative, calllocalnative
Structure:
| Arguments | Definition |
|---|---|
NativeFunctionName |
Name of the native function
|
{Arguments...} |
Many values; as many as you need to be able to fulfill every argument of the NativeFunctionName function
|
Functions:
| Function | Usage |
|---|---|
CallNative |
Calls a native function implemented in Python in the global scope, which adds additional functionality to Stacky.
|
CallLocalNative |
Calls a native function implemented in Python in the local scope, which adds additional functionality to Stacky.
|
Note: The CallNative function has two different styles, a global and local style.
Loop
Instruction: loop
Structure:
| Arguments | Definition |
|---|---|
Body |
Body code |
Example:
define x 0 loop push x callnative print callnative inc pop x end
Function:
| Function | Usage |
|---|---|
Loop |
An instruction to indicate a start of a loop block, which repeats indefinitely and executes code inside of Body until it is terminated by Exit
|
Exit
Instruction: exit
Structure:
| Arguments | Definition |
|---|---|
Depth |
How many scopes to terminate
|
Functions:
| Function | Usage |
|---|---|
Exit |
Terminates Depth amount of scopes recursively until the desired depth is reached or there are no more scopes left to terminate
|
Function
Instruction: function
Structure:
| Arguments | Definition |
|---|---|
FunctionDefinitonName |
Name of the function being defined |
{Arguments...} |
A series of named arguments for the function |
Example:
function foo(a, b) push a push b callnative add end
Function:
| Function | Usage |
|---|---|
Function |
An instruction to indicate a function definition. See example code above for usage |
Note: You can use functions as a value by just referencing the name. See example below for live function usage
define fooAlias foo
Apply and ApplyLocal
Instruction: apply, applylocal
Structure:
| Arguments | Definition |
|---|---|
FunctionReference |
Name or variable of the function to be used. This may be a native function
|
Functions:
| Function | Usage |
|---|---|
Apply |
Applies the container on top of the stack (either a list or tuple) to the function FunctionReference in the global scope
|
ApplyLocal |
Applies the container on top of the stack (either a list or tuple) to the function FunctionReference in the local scope
|
Note: The Apply function has two different styles, a global and local style.
Note: Under the hood, this invokes the call or callnative functions, depending on the actual function. If there is an issue with them, it will affect this instruction too.
Return
Instruction: return
Structure:
| Arguments | Definition |
|---|---|
Value |
Any valid PyStacky value |
Functions:
| Function | Usage |
|---|---|
Return |
Returns the value Value to the previous function scope
|
Control Flow
Internal: Condition
Condition is an internal class representing any simple Boolean expression (Boolean expressions with only a comparison operator)
Structure:
| Arguments | Definition |
|---|---|
Left |
Left node of the condition. Can be a BooleanExpression
|
Operator |
Comparison operator |
Right |
Right node of the condition. Can be a BooleanExpression
|
Valid values for Operator: ==, !=, >, <, >=, <=
Internal: BooleanExpression
BooleanExpression is an internal class representing a Boolean expression
Structure:
| Arguments | Definition |
|---|---|
Left |
The left Condition of the BooleanExpression
|
Operator |
Boolean operator |
Right |
The right Condition of the BooleanExpression
|
Valid values for Operator: &&, ||
If
Instruction: if
Structure:
| Arguments | Definition |
|---|---|
Condition |
The Condition or BooleanExpression to be evaluated
|
Body |
Body code |
Example:
if a > b push "Greater" end
Function:
| Function | Usage |
|---|---|
If |
Executes the code inside Body if Condition evaluates to True
|
Elif
Instruction: elif
Structure:
| Arguments | Definition |
|---|---|
Condition |
The Condition or BooleanExpression to be evaluated
|
Body |
Body code |
Example:
if a > b push "Greater" elif a < b push "Less" end
Function:
| Function | Usage |
|---|---|
Elif |
Executes the code inside Body if Condition evaluates to True, and if the header If statement evaluates to False
|
Else
Instruction: else
Structure:
| Arguments | Definition |
|---|---|
Body |
Body code |
Example:
if a > b push "Greater" elif a < b push "Less" else exit 1 end
Function:
| Function | Usage |
|---|---|
Else |
Executes the code inside Body if the header If statement evaluates to False and all other Elif statements are False
|
Import
Instruction: import
Structure:
| Arguments | Definition |
|---|---|
PackageName |
Name of the the package to be imported |
Functions:
| Function | Usage |
|---|---|
Import |
Imports a package inside of the packages directory
|
Extra information on usage of this instruction:
To create a package, go into the packages directory. You may see some already created built-in packages. To test that the interpreter can import packages successfully, attempt to import the package example and look for the success message in console. A package may only contain other Import instructions and Function instructions (of course, inside of the Function there may be any instruction).
Live Functions
A live function, internally represented as a FunctionInstance is a function that can be pushed, popped, stored, and called. This is useful for more complex programs, as you can manipulate when and what functions are used. Also, instead of pushing every single argument on the stack, you can use the apply instruction to apply a tuple or list of arguments to the function.
WARNING:
Attempting to create a string resembling a FunctionInstance (in other words, creating a string starting with "<FunctionInstance..." will result in a RuntimeError. Unlike creating a function with the name GLOBAL, this is disallowed.
Scopes
GLOBAL scope
Any stack entries or variable entries in this scope can be accessed anywhere, by any function. These variables are not deleted when a function ends. Functions can directly interact with this stack.
WARNING:
Attempting to name a function GLOBAL will succeed, but will corrupt the local scope tracker self.scope of Evaluator (the evaluator assumes that setting the scope to GLOBAL is exiting all functions). This will most likely cause unintended behavior involving scopes, and make scope-dependent functions like PushLocal and CallLocalNative behave incorrectly.
Local scopes
Any stack entries or variable entries in a local scope can only be accessed and modified by the owner of the scope. For example, if I called a function named foo, a local scope named foo will be registered, and only the exact instance of foo can access and modify the contents of it. All local scopes are directly displayed on the secondary tkinter widget popup.
Native Functions
A native function is a PyStacky function that is implemented in Python instead of Stacky, which adds some features that could not be created with just Stacky alone (like simple arithmetic). These functions, instead of being invoked by Call, are invoked by either CallNative or CallLocalNative. They are internally called by InvokeNative.
add, sub, mul, intdiv, div
These 5 arithmetic functions allow you to perform calculations on values on the stack.
| Function | Before | After |
|---|---|---|
add |
... a b |
... (a + b)
|
sub |
... a b |
... (a - b)
|
mul |
... a b |
... (a * b)
|
div |
... a b |
... (a / b)
|
intdiv |
... a b |
... (a // b)
|
print, printWithPop
These native functions allow you to output text into the available sys.stdout
| Function | Before | After |
|---|---|---|
print |
... a |
... a
|
printWithPop |
... a b |
... a
|
dup, swap, over, rot
Some stack manipulation functions
| Function | Before | After |
|---|---|---|
dup |
... a |
... a a
|
swap |
... a b |
... b a
|
over |
... a b |
... a b a
|
rot |
... a b c |
... b c a
|
nip, tuck, depth, pick, roll
Some more stack manipulation functions
| Function | Before | After |
|---|---|---|
nip |
... a b |
... b
|
tuck |
... a b |
... a b a
|
depth |
... {...} |
... {LEN(STACK)}
|
These functions have more complex behavior
| Function | Effect |
|---|---|
pick |
Pushes the nth element of the stack to the top, without removing it
|
roll |
Pushes the nth element of the stack to the top, and shifting all elements down (removing the value from its original position)
|
Note: n in this context is the top element of the stack, and is popped off when pick or roll is called
mod, neg, abs, min, max
Some complex arithmetic functions
| Function | Before | After |
|---|---|---|
mod |
... a b |
... (a % b)
|
neg |
... a |
... -a
|
abs |
... a |
... (a < 0 ? -a : a)
|
min |
... a b |
... (a > b ? b : a)
|
max |
... a b |
... (a > b ? a : b)
|
pow, inc, dec, round
Some more complex arithmetic functions
| Function | Before | After |
|---|---|---|
pow |
... a b |
... (a ^ b)
|
inc |
... a |
... (a + 1)
|
dec |
... a |
... (a - 1)
|
round |
... a b |
... {ROUND(a, b)}
|
strconcat, strlen, substr
These functions manipulate a string on the stack
| Function | Effect |
|---|---|
strconcat |
Joins two string together |
strlen |
Gets the length of the string |
substr |
Gets a substring from a string, from a start value to end, exclusive
|
Note: start and end in this context are elements in the stack, and is popped off when substr is called
iterlen, getelement, setelement, iterappend, iterclear
These functions manipulate iterables directly on the stack
| Function | Before | After |
|---|---|---|
iterlen |
... lst |
... {LEN(LST)}
|
getelement |
... lst idx |
... {LST[IDX]}
|
setelement |
... lst idx val |
... {LST[IDX] = VAL}
|
iterappend |
... lst val |
... {LST.APPEND(VAL)}
|
iterclear |
... iter |
... {ITER.CLEAR()}
|
delelement, iterextend, sort, iterpop
Some more functions that manipulate iterables
| Function | Before | After |
|---|---|---|
delemenet |
... lst idx |
... {DEL LST[IDX])}
|
iterextend |
... lst1 lst2 |
... {LST1.EXTEND(LST2)}
|
sort |
... lst reversedOptional |
... {SORTED(LST, REVERSE=REVERSEDOPTIONAL)}
|
iterpop |
... lst idxOptional |
... {LST.POP(IDXOPTIONAL)}
|
totuple, tolist
These two functions convert between lists and tuples
| Function | Before | After |
|---|---|---|
totuple |
... lst |
... tup
|
tolist |
... tup |
... lst
|
dump
Prints the current scope's stack to console
dictgetvalue, dictsetvalue, dictkeys, dictvalues
These native functions manipulate the contents of a map
| Function | Before | After |
|---|---|---|
dictgetvalue |
... dct key defaultOptional |
... {DCT.GET(KEY, DEFAULTOPTIONAL)
|
dictsetvalue |
... dct key value |
... {DCT[KEY] = VALUE}
|
dictkeys |
... dct |
... {DCT.KEYS()}
|
dictvalues |
... dct |
... {DCT.VALUES()}
|
Containers
A container, or iterable, is a data type in PyStacky that can hold more than one value. Also, a Map is a unique type of container since it has keys that map to values, hence the name of "map".
All containers are displayed as a string, with a prefix and then a container holding all elements of the iterable.
Lists
A list is a mutable collection of values. A list may contain any value, from a number to another list (a list in lists is called a matrix of some dimension). A PyStacky list is internally represented as a Python list, and displayed as a string:
L{Elements...}
Where the prefix, L, indicates a list.
Tuples
A tuple is an immutable collection of values, meaning its contents cannot be changed after creation in any way. Essentially, a tuple is basically a list, except it can't be modified. A PyStacky tuple is internally represented as a Python tuple, and displayed as a string:
T{Elements...}
Where the prefix, T, indicates a tuple.
Maps
A map (also known as a dictionary in some languages, like Python) is a collection of keys and values, where each unique key maps (corresponds) to a value. A PyStacky map is internally represented as a Python dictionary, and displayed as a string:
M{{keys...} : {values...}}
Where the prefix, M, indicates a map.