Special Forms
In Scheme some forms are not handled as plain function application. This document lists the planned special forms for the language, along with their implementation status.
The set of forms are derived from those in R7RS.
Lambda Expressions
(lambda <formals> <expression>+)
Returns an anonymous procedure which binds its arguments to
<formals>
and then evaluates a number of <expression>
s in the new
environment.
Formals can be either a single identifier to bind the parameter list
to, or a list which the parameters should be matched against. If the
list contains .
then following parameters are bound to a list to
following argument.
e.g.:
The expression (lambda a (+ 1 2))
defines a procedure that takes any
arguments and binds the list to a
in the lambda’s environment.
The expression (lambda (b) (+ 1 2))
defines a procedure that takes a
single argument and binds that to b
in the lambda’s environment.
The expression (labmda (c . d) (+ 1 2))
defines a procedure that takes
a single argument and an optional number of following arguments. The
first argument is bound to c
in the lambda’s environment and all
remaining arguments are bound to a list d
in the lambda’s environment.
Implementation status
All forms are lambdas are bound and lowered. Lambdas are implemnted as instances
of Func<object[],object>
. Implementation was live-streamed. Checkout YouTube
for the stream archive.
Lexical Bindings
(let (<init>+) <expression>+) (let* (<init>+) <expression>+) (letrec (<init>+) <expression>+)
Let bindings create a new environment and introduce bindings to
them. In the first ‘basic’ let
each init
is evaluated in the
parent environment. For a let*
each initialiser is evaluated in the
child environment sequentially allowing the new bindings to reference
previous ones. In the final letrec
form each new binding is
initialised with some placeholder value before the intialiser
expressions are evaluated in the child environment allowing full
mutual recursion.
Implementation status
Lexical bindings are implemneted.
Definitions
(define <variable> <expression>?) (define <formals> <expression>+)
Define statements bind variables to new storage location and assign
them a value. Simple define
forms without an lambda
, but only up to the first non-definition expression.
Procedure definitions are just lambdas bound to the name that occurs
as the first element of the <formals>
definition.
Implementation status
Variable definitions are bound and lowered. Function definitions are bound
as definitions of lambdas and rely on lambda
support for lowering.
Internal deifnitions (that is a define
that isn’t in the root) aren’t properly
handled. Internal definitions should be mutually recursive. Definitions in
internal contexts should only be permitted before the first non-definition
expression.
Assignments
(set! <variable> <expression>)
Set expressions assign the result of <expression>
to the location
that <variable>
is currently bound to. If <variable>
is unbound
then the expression raises an error.
Implementation status
Assignments are bound and lowered.
Quoting
(quote <expression>) '<expression> ,<expression>
Quote expressions evaluate to the external representation of the expression rather than evaluating the expression directly. For literals there is no difference. For lists this skips application and allows creation of lists directly.
Implementation status
Simple quoted forms are implemented. As well as the standard ’ character for
quoting we also support ’
for compatibility with example code in LaTeX docs.
Quasiquote is not supported yet.
Conditionals
(if <cond> <if-true> <if-false>?) (when <cond> <if-true>+) (unless <cond> <if-false>+)
An if expression evaluates the <cond>
ition followed by one of either
<if-true>
or <if-false>
. This defers the evaluation of the
consequent expression until after the variable check. The when
and unless
forms allow executing multiple expressions in response to true or or false
conditions and are shorthands for an if
and begin
.
(and <expression>*) (or <expression>*)
Boolean conditional expressions. Both lazily evaluate the given
expression returning the result of the last expression that needed to
be evaluated to derive the overall truthiness of the expression. An
empty and
is implicitly truthy, an empty or
implicitly falsey.
(cond <clause>+)
Where each <clause>
is (<predicate> <expression>+)
. Evaluates the
first <clause>
’s body where the <predicate>
is truthy. The final
predicate may be else
, which is always considered truthy.
(case <key> <case>+)
Where <case>
is ((<value>+) <expression>+)
. Evaluates <key>
once
and then evaluates the body of whichever <case>
contains the
resulting value in <value>
s. The final case may use else
in place
of the value list to provide a default.
Implementation status
The if
conditional special form is implemnted. The and
, or
, when
and
unless
forms are implemented as builtin macros. The cond
and case
forms
may need macro hygene to be implemented properly.
Sequence
(begin <expression>+)
The begin
expression evaluates each inner expression
in sequence
and returns the result of the final expression.
Implementation status
The begin special form is implemented.