docs/syntax/assignment.md
Assignment syntax in Enso is fairly magical, given that it is the language's syntax for monadic bind.
<!-- MarkdownTOC levels="2,3" autolink="true" -->Assignment in Enso operates as follows:
Nothing, and does not return the value that
is assigned to it.The assignment operator has myriad uses, and is used to define variables, functions, extension methods, and to perform pattern matching. Each different case will see an appropriate desugaring applied (see below).
Please note that not all occurrences of the = operator are assignments in
the general sense. The above rules do not apply when using said operator to pass
arguments by name.
If the left hand side of an assignment is syntactically a prefix application chain, where the left-most name is a variable name, the assignment is considered to introduce a function definition (the syntax sugared version).
For a prefix chain a b c = ..., this operates as follows:
a is bound in the enclosing scope, and is called the 'function
name'.b and c (the 'function arguments') are converted into nested
lambda arguments in the function body.In essence, the above example is equivalent to:
a = b -> c -> ...
Please note that by the rules of naming specified previously, if an operator
occurs in the same position as a it will also be defined.
If the left hand side of an assignment is syntactically a prefix application chain, where the left-most name is a type name, the assignment is considered to introduce a pattern match binding.
It operates as follows for code consisting of a prefix chain A b c = expr and
trailing code tail....
A b c = expr
tail...
expr.A, b, and c are used in a case expression branch's
pattern. The branch's expression is tail....error.As each branch in a case expression has its own scope, this desugaring means
that the names b and c are made visible in the scope where the pattern match
binding occurs. This is due to the fact that pattern match branches are lambda
expressions, and reuse the same scoping rules.
This also works for operators in an infix position, where its operands will be matched against.
There are two cases where an assignment creates an extension method:
., this assignment is considered to introduce an extension
method.this
with an explicit type ascription, this is also considered to introduce an
extension method.This syntax for extension methods works as follows:
.) defines the type on
which the extension method is created.this argument is inserted with that type at the start of the
arguments list.My_Type.method_name a b c = ...
This syntax for extension methods works as follows:
this argument type is used to define the type on which the extension
method is created.this and all remaining arguments are desugared to lambda arguments.method_name (this : My_Type) a b c = ...
In order to aid with disambiguation, any binding made in the root scope without
an explicit target is implicitly defined on a type representing the current
module. For example, a binding main = ... is implicitly here.main = ....
This works as follows:
here.name if not ambiguous, but can be disambiguated by
using here.name where necessary.