openbirch written in rust
Find a file
2025-03-20 12:29:12 +01:00
src did some grinding off camera 2025-03-20 12:27:27 +01:00
.gitignore initial commit 2025-02-11 19:27:56 +01:00
adamina.ttf the ui is finally here 2025-02-14 00:10:39 +01:00
adamina.woff the ui is finally here 2025-02-14 00:10:39 +01:00
Cargo.lock cleaned up some code 2025-02-24 02:37:50 +01:00
Cargo.toml cleaned up some code 2025-02-24 02:37:50 +01:00
flake.lock parsing 2025-02-20 02:08:16 +01:00
flake.nix cleaned up some code 2025-02-24 02:37:50 +01:00
mononoki.ttf the ui is finally here 2025-02-14 00:10:39 +01:00
README.md fixed readme 2025-03-20 12:29:12 +01:00
test.txt did some grinding off camera 2025-03-20 12:27:27 +01:00
xits-italic.ttf AUGHR 2025-02-13 16:50:36 +01:00

Openbirch Rust

Openbirch rewritten in rust.

Very messy and bad, im gonna start the umpteenth rewrite soon.

Features

  • Constants (numbers)
    • Addition
    • Subtraction
    • Multiplication
    • Division
    • Arbitrary float precision
  • Sets (or lists, arrays, etc)
    • Definition
    • Multiplication with constants
    • Concattenation
    • Index operator
  • Functions
    • Native functions
    • User defined functions
    • Currying
    • Closures
    • Calling
  • Scopes
    • Shadowing variables
  • Ranges
    • Defining ranges (1..5 is a range of [1..5))
    • Iterating ranges
    • Evaluating ranges (very hacky, but defining a Set of length 1 with a range expands said range into the set, eg [1..3] becomes [1,2])
  • Loops
    • Infinite loops (loop ... end block)
    • For loops (for x in y ... end block)
    • Break keyword
  • Match expression
  • If expression
    • If expression
    • If-else expression

Wanted

  • More concise syntax, i dont like how it is right now
  • Fix stack overflow with recursive functions (internally convert to loops)
  • Generally implement more
  • Implicit multiplication (may not be possible to implement non-ambiguously)
  • Differentiation
  • Integration
  • Better error handling (i was lazy and skimped on errors, bad move)

Syntax

Every Openbirch program is made up of 0 or more expressions.

An expression is anything from a binary operation like 2+2 to function calls f(x) and even assignments x := 5.

All expressions return a value. For expressions that "dont" they return an Empty, which cant be used for anything and will error if used in other operations (eg. 2+{Empty}).

Definition

Variables can be defined with a define expression.

x := 5 # define x as 5

print(x+x) # prints 10

As openbirch is a symbolic language variables can be used before assignment

y := x^2

print(y) # prints x^2

x := 5

print(y) # prints 25

Scopes

Some expressions define a scope, where all defined variables inside will be deleted once the scope ends.

Expressions that create a scope include, but are not limited to,

  • If-else
  • Loop
  • Functions
  • Closures

If a variable is defined outside a scope it will be shadowed inside the scope. What this means is that inside the scope the variable will have the shadowed value, while outside the scope it will have the previous value.

x := 5 # Global scope

print(x) # prints 5

if true then    # Define a new scope
    x := 5000 # Shadow the value of x
    print(x)  # prints 5000
end             # Scope ends here

print(x) # prints 5

Assignment

Since you may want to change the value of a variable outside the current scope you can use an assignment rather than a definition.

x := 5

if true then
    x <- 500 # Assign to x rather than defining it and shadowing it
end

print(x) # prints 500

If-else

If expressions are defined as such

if {condition} then
    # 0 or more statements
end

and if-else as

if {condition} then
    # 0 or more statements
else 
    {expression}
end

Since if is an expression the body of the else branch can be another if expression, in which case only 1 end keyword is needed.

if {condition} then
    # 0 or more statements
else if {condition} then
    # 0 or more statements
end

Since all expressions evaluate to a value the value of the if expression is the resulting value of the last statement in the chosen branch, eg.

x := if true then
    # Evaluate some expressions
    2+2
    f(x)
    y := f(f(x))
    # Last expression is returned
    5
else
    0
end

print(x) # prints 5

if a branch is empty then Empty is returned.

Loops

Currently the only type of loop is an infinite loop.

loop
    # This will repeat forever
end

Running

Linux

$ cargo run

Nixos

$ nix develop
$ cargo run

Windows

idfk, havent used that shit in years, but probably just cargo run.

MacOS

never used, but again probably cargo run