# Examples ``` fn returnsFortyTwo(a in 'int, b in 'int) returns 'int 42 ``` ``` fn returnsFortyTwo(a: 'int, b: 'int) returns 'int[crashable] if a == 42 then crash else 42 ``` ``` fn printsHello() returns 'nothing[stdout] println "hello" ``` ``` fn printsManyThings(a: is Iterable(is Showable)) returns 'nothing[complexity precise a] foreach a println ``` ``` fn sometimesPrintsThings(a: 'list['int]) returns 'nothing[worstcase a, bestcase 0, stdout] any a printIfNot42 fn printIfNot42(a: 'int) returns bool[stdout] if a == 42 then return true else [print "hello"] ``` ``` type bool = true | false type int = 0.. type non_empty_list 'T = first_value 'T, rest: list 'T ``` ``` {- TODO: this syntax is kind of rough. How is this an expr? Do we need generator funcs? -} constraint prime a: 'int = forall (x in 'int < a) (a / x is 'int holds) ``` # Expressions ## If ```bnf <if> ::= "if" <expr> "then" <expr> <else> <else> ::= "else" <expr> | ε ``` ## Function Call ``` <call> ::= ident <args> <args> ::= <expr> <args> | ε ``` ## let..in ``` <let_in> ::= "let" <assignment>+ "in" <expr> <assignment> ::= ident <type_annotation>? "=" <expr> <type_annotation> ::= "in" <ident><effects>? <effects> ::= "[" <effect>+ "]" <effect> ::= ident <effect_params> ``` # Declarations ## Type ``` <data_type> ::= "data" "type" ident "=" <named_field>* <named_field> ::= ident "in" ident <effects>? <sum_type> ::= "sum" "type" ident "=" <named_variant>* <named_variant> ::= ident <contained_ty>? <contained_ty> ::= ident <effects>? ``` ## Function ``` <fn_decl> ::= <fn_signature> <expr> <fn_signature> ::= "fn" ident <params> "returns" ident <effects>? ``` ## Constraint ``` <constraint_decl> ::= "constraint" ident <constraint_param>* = <constraint_body> <constraint_param> ::= ident ident? <effects>? <constraint_body> ::= "intrinsic" | <expr> ``` ## Typeclass ``` <typeclass> ::= "typeclass" ident <fn_signature>* ``` ``` <instance_of> ::= ident "is" "instance" "of" <typeclass> <fn_decl>* ``` ## Sugar ### field access lambda ``` _.field_name // is the same as \x -> x.field_name ```