Skip to content
FutureBlitz

    Install

    Guide

    Coming from C# or Python

    What C# and Python programmers will find familiar in FutureBlitz, and what works differently.

    FutureBlitz has much of what C# and Python have, written in words rather than braces or indentation, and compiled to a native executable with no runtime to install.

    At a glance

    C#PythonFutureBlitz
    var x = 1;x = 1Local x = 1
    int, long, doubleint, floatInt, Int64, Float, Double, and sized integers
    string? nameOptional[str]name: String?, checked by the compiler
    class, structclass, @dataclassClass, a reference; Struct, a value
    interfaceProtocolInterface, with default Methods
    List<T>, Dictionary<K, V>list, dictT[], Map<K, V>, {"a": 1}
    foreach (var x in xs)for x in xs:For x In xs ... End For
    $"{a} and {b}"f"{a} and {b}""{a} and {b}"
    x => x * 2lambda x: x * 2Function(x: Int) => x * 2
    throw, try, catchraise, try, exceptThrow, Try, Catch, and Throws on what can throw
    async, await, Task<T>async, awaitAsync Function, Await, Task<T>
    Task.Run, Parallel.Forthreading, multiprocessingSpawn, Parallel For, on every core
    garbage collectorreference counting and a collectorreference counting, no collector
    NuGetpipfb add, from the registry

    Blocks end with words

    A block ends with End and what it was, so there are no braces, and indentation is style, which fb fmt keeps.

    Import std.core
    
    Function Grade(score: Int): String
        If score >= 90
            Return "A"
        ElseIf score >= 75
            Return "B"
        End If
        Return "C"
    End Function
    
    For score In [95, 80, 60]
        Print("{score}: {Grade(score)}")
    End For
    Output
    95: A
    80: B
    60: C

    Types are checked before it runs

    Like C#, and unlike Python, every value has a type the compiler knows, though most are inferred. A value that can be missing has a type that says so, and the compiler won’t let code use it before checking.

    Import std.core
    Import std.collections
    
    Local stock = {"apples": 12, "plums": 7}
    Local pears: Int? = stock.Get("pears")
    Print(pears ?? 0)
    If pears != Null Then Print(pears + 1)
    Print(stock.Get("plums") ?? 0)
    Output
    0
    7

    Errors say what can throw

    A Function that can throw says so with Throws, and a call to it is marked with Try, so a reader sees each place an error can come from. A panic, like an index out of range, is a bug, not an error to catch, and it stops the program with a stack trace.

    Import std.core
    
    Class EmptyCart Extends Error
    End Class
    
    Function Total(prices: Int[]): Int Throws EmptyCart
        If prices.Count == 0 Then Throw EmptyCart("nothing to pay for")
        Local sum = 0
        For price In prices
            sum += price
        End For
        Return sum
    End Function
    
    Try
        Print(Try Total([250, 125]))
        Print(Try Total([]))
    Catch e As EmptyCart
        Print("can't total: {e.Message}")
    End Try
    Output
    375
    can't total: nothing to pay for

    Memory without a collector

    Objects are reference-counted: one is freed the moment the last reference to it goes, so a program never pauses for a collector, and a Class’s Destroy Method runs at a known time, like C#‘s Dispose or Python’s with, with nothing to call. Two objects that refer to each other need one reference to be Weak, so the pair can go; in a debug build, fb reports what leaks.

    Threads are checked

    Spawn runs work on a pool of worker threads, and the compiler checks what it takes: only values that are safe to share between threads, so there are no data races to find later. Async and Await let a Function wait for I/O or for another task without blocking its thread, as in C#.

    Packages and tools

    One command does what dotnet or pip with a formatter, a test runner, and a build tool do: fb new, fb run, fb test, fb fmt, fb add, and fb publish. Tools has each one.

    Report an issue with this page or with FutureBlitz on GitHub.