Patterns and bindings

Patterns and pattern matching

Patterns occur in several syntactic contexts in Timber (e.g. in the left hand sides of bindings, lambda expressions and case alternatives). Syntactically, patterns form a subset of expressions; a pattern is one of the following:

At run-time, patterns are matched against values. Pattern-matching may succeed or fail; in the former case the result is a binding of the variables in the pattern to values. The rules are as follows:

The special "wildcard" variable _ may be used in patterns; in contrast to other variables, it is not bound by pattern-matching.

A consequence of the way pattern-matching is done is that patterns must be linear; no variable may occur more than once in a pattern.


Syntactically, bindings are divided into type signatures and equations. Equations are either function bindings, pattern bindings or instance bindings for type classes.

With the exception of struct expressions and the second alternative form for instances (which is immediately desugared to a form with a struct expression), bindings in a sequence are mutually recursive. This amounts to bound variables of all types and is independent of whether the corresponding right-hand sides need further evaluation or not.

Evaluation of bindings takes place in dependency order, but follows the declared order for bindings that are truly mutually dependent. This declared order is significant for one specific reason: evaluation of each binding must be able to complete without looking into the actual value of any of its forward references. Failure to do so will result in a run-time error.

f 0 = 1
f n = n * f (n-1)Ordinary recursive function binding
g h 0 = 1
g h n = n * h (n-1) Non-recursive higher-order function binding
f' = g f'Recursive binding of f' (equivalent to f)
x = 1 : yLegal forward reference
y = 2 : xOk, both x and y are cyclic lists
a = 1 : b
b = head a : []Legal backward reference (ok to look into the value of a)
a' = head b' : []Illegal forward reference (must look into the value of b')
b' = 2 : a'Not reached (run-time error on previous line)

In addition, binding sequences are subject to the following syntactic restrictions: