on the Java Virtual Machine (JVM). The Flix compiler performs whole program compilation, eliminates polymorphism via monomorphization, and uses tree shaking to remove unreachable code. Monomorphization avoids boxing of primitive values at the cost of longer compilation times and larger executable binaries. Flix has some support for interoperability with programs written in Java. Flix supports tail call elimination which ensures that function calls in tail position never consume stack space and hence cannot cause the call stack to overflow. Since the JVM instruction set lacks explicit support for tail calls, such calls are emulated using a form of reusable stack frames. Support for tail call elimination is important since all iteration in Flix is expressed through recursion. The Flix compiler disallows most forms of unused or redundant code, including: unused local variables, unused functions, unused formal parameters, unused type parameters, and unused type declarations, such unused constructs are reported as compiler errors. Variable shadowing is also disallowed. The stated rationale is that unused or redundant code is often correlated with erroneous code A Visual Studio Code extension for Flix is available. The extension is based on the Language Server Protocol, a common interface between IDEs and compilers being developed by Microsoft. Flix is open source software available under the Apache 2.0 License. Examples Hello world The following program prints "Hello World!" when compiled and executed: def main(): Unit & Impure = Console.printLine("Hello World!") The type and effect signature of the main function specifies that it has no parameters, returns a value of type Unit, and that the function is impure. The main function is impure because it invokes printLine which is impure. Algebraic data types and pattern matching The following program fragment declares an algebraic data type (ADT) named Shape: enum Shape { case Circle(Int), // has circle radius case Square(Int), // has side length case Rectangle(Int, Int) // has height and width } The ADT has three constructors: Circle, Square, and Rectangle. The following program fragment uses pattern matching to destruct a Shape value: def area(s: Shape): Int = match s { case Circle(r) => 3 * (r * r) case Square(w) => w * w case Rectangle(h, w) => h * w } Higher-order functions The following program fragment defines a higher-order function named twice that when given a function f from Int to Int returns a function that applies f to its input two times: def twice(f: