A Timber program may contain two kinds of comments:
A Timber program consists mainly of definitions that give meaning to names. There are six separate namespaces in Timber:
Names are simple or qualified; the latter are used to disambiguate names defined in different modules.
Simple names come in two lexically distinct forms, identifiers and operators.
An identifier consists of a letter followed by zero or more letters, digits, single quotes and underscores. The initial letter must be upper case for constructors, type constructors and module names, and must be lower case for variables, selectors and type variables. The following lexically correct identifiers are keywords of the language and may not be used as names:
action after before case class data do default else elsif forall if import in instance let module new of private request result struct then type typeclass use where
An operator is a sequence of one or more symbol characters. The symbol characters are defined by enumeration: :!#$%&*+\<=>?@\^|-~. An operator starting with : is a constructor; otherwise it is a variable. Only variables and constructors have operator forms; the other four namespaces contain only identifiers. The following lexically correct operators are keywords and may not be used as names:
. .. :: := = \ \\ | <- -> --
An identifier may be used as an operator by enclosing it in backquotes; `elem` is an operator. Conversely, an operator may be used as an identifier by enclosing it in parentheses; (+) is an identifier.
Examples:
Names | Possible namespaces |
---|---|
Color, T3, T_3, T_3' | constructors, type constructors, module names |
x, env, myTable, a', x_1 | variables, selectors, type variables |
+, #=#, @@ | variables |
:, :++: | constructors |
#3 | ILLEGAL; mixture of operator and identifier symbols. |
The precedence and associativity of operators are determined by their syntax. The operators in the following table are listed in decreasing precedence, i.e. an operator that appears in a later row binds less tightly. Function application, denoted by juxtaposition, binds tighter than all operators.
Operators | Associativity |
---|---|
@ | Right |
^ | Right |
* / `div` `mod` | Left |
+ - | Left |
: ++ | Right |
== /= < > <= >= | None |
&& | Right |
|| | Right |
>> >>= | Left |
$ | Right |
The operators in the table above are defined in the Prelude, but can be redefined in user modules, except for the following three exceptions:
In harmony with this, the empty list has the (lexically illegal) name [].
This means that, if evaluation of a in a && b gives False as result, the result of the complete expression is False and b is not evaluated (and, in particular, a runtime error or non-termination that would occur during evaluation of b is avoided).
Similarly, if the left operand to || evaluates to True, the result of the complete expression is True without evaluating the right operand.
Thus, semantically speaking, && and || are not operators at all but special expression-forming constructs.
Timber modules are used to manage namespaces. In this mechanism, simple names are extended to qualified forms, where the simple name is prefixed by the name of the module where it is defined. To allow several modules with the same name in a system, module names themselves may be qualified.
A qualified module name is a sequence of simple module names interspersed with periods, such as Data.Functional.List. The module name (given in the module header) is here just List, but the full name must be used by importing clients and is also used by the Timber installation to store and retrieve modules in the file system. Exactly how this is done is installation-dependent.
Imagine a module Dictionary, which defines among others the names insert and |->. An importing module may refer to these names using the qualified forms Dictionary.insert and Dictionary.|-> in order to avoid possible name conflicts. See the modules page for more information on import and use of other modules.The simple name that is the suffix of a qualified name decides if the name is an operator or an identifier and if it is a constructor or not.
A qualified name may not be used at a defining occurrence, only when a name is used. (The module prefix is uniquely determined by the module name, hence superfluous in the definition.)