Special Forms¶
Special forms are pseudo-functions handled directly by the evaluator. They cannot be extended or altered.
Sequence Forms¶
There are three sequence special forms: begin, and and or.
They all take a sequence of expressions and start to evaluate them,
one by one. They differ in how many of the expressions they evaluate,
what they return and what they return if no expressions are passed.
begin ...
and ...
or ...
begin¶
begin evaluates all of the expressions and returns the value of
the last expression.
This is the normal block of code behaviour.
If no expressions are passed, begin returns #<void>.
and¶
and evaluates all of the expressions unless an expression returns
#f at which point and also returns #f. The remaining
expressions are not evaluated.
If all of the expression return a true value then and returns
the value of the last expression.
If no expressions are passed, and returns #t.
or¶
or evaluates all of the expressions until an expression returns a
true value and or returns that value. The remaining expressions
are not evaluated.
If all of the expressions return #f then or returns #f.
If no expressions are passed, or returns #f.
not¶
The not special form is used to inverted the sense of a boolean.
There is a function variant, not/function, for where a function is required.
escape¶
The escape special form is used to prevent the reader implementing
operators. The default reader escape character is \.
escape e
\e
escape continues evaluation with its argument.
For example, the infix operator + expects numbers as arguments so
we might make a mis-type before escaping it:
Idio> apply + 1 2 3
...:^rt-parameter-type-error:bad parameter type: '#<PRIM apply>' a primitive is not a number
...
#<unspec>
Idio> apply \+ 1 2 3
6
quote¶
The quote special form is used to prevent the evaluator evaluating
its argument. The default reader quote character is '.
quote e
'e
quote returns its argument unevaluated.
For example, any parenthesised list is considered a function call so we need to quote any literal lists:
Idio> printf "a list %s\n" (1 2 3)
...:^rt-function-error:cannot invoke constant type: detail (1)
...
Idio> printf "a list %s\n" '(1 2 3)
a list (1 2 3)
#<unspec>
quasiquote¶
The quasiquote special form is the basis for expanding
templates.
#T{ ... }
function/name¶
The function/name special form is used to return a function value,
commonly called a closure.
function/name name formals [docstr] body
name is the name to be associated with the function.
formals declares the parameters for the closure and arguments passed to the function are available through the named parameters within the body of the function.
formals takes several forms, see closure parameters and the extended forms in function*/name.
The optional docstr allows the user to describe their function. This text will be used in help output as well as used to generate documentation like this. It should take the form of reStructuredText targeting the Sphinx documentation system.
body is a single expression although commonly a block is used as a synonym for the begin sequence special form.
function/name exists largely because debugging with anonymous
functions becomes difficult especially when that anonymity exists only
because of the deliberate enforcement of anonymity in the evaluator.
(define (foo a b) ...)
was rewritten to:
(define foo (function a b) ...)
but can now be rewritten to:
(define foo (function/name foo a b) ...)
which keeps the normal form and also ensures the name of the function value is carried through.
function¶
The function special form is used to return a function value,
commonly called a closure.
function formals [docstr] body
function only differs from function/name in the absence of a name. function is a simple
wrapper to function/name passing (gensym 'anon) as the
function’s name.
function+¶
The function+ special form is used to extend the current
function’s argument frame. It appears when a function’s body is
rewritten to a normal form.
Users are not expected to use this special form.
if¶
The if special form is the fundamental test and branch mechanism.
if condition consequent alternative
If the expression condition evaluates to true then evaluate consequent otherwise evaluate alternative.
Whichever of consequent or alternative is evaluated, its result is
the value returned by if.
If condition evaluates to #f and there is no alternative then
if returns #<void>.
cond¶
The cond special form is an abstraction of the if Special Form. It is equivalent to many languages’ if
... elif ... elif ... else ....
cond clauses
clauses is a list of clauses where each clause can take the form:
(condition ...)If the expression condition evaluates to true then evaluate … returning its value as the value from
cond.(condition => f)If the expression condition evaluates to true then call the function f with the result of condition and return the result of f as the value from
cond.This is the anaphoric if expression, roughly equivalent to:
it := condition if it { f it }where condition is evaluated and the result recorded. If the result was true then call f with the result as an argument.
(else ...)Evaluate … returning its value as the value from
cond.The
elseclause can only appear as the last clause
If no clauses satisfy and there is no else clause, cond
returns #<void>.
set!¶
The set! special form modifies memory, hence the ! in the
name. It has an = synonym and an = reader operator.
set! var value
= var value
var = value
Note
Technically, set! doesn’t modify any value but changes a
reference to point to a different value.
From a user perspective, the variable has a different value.
define-template¶
The define-template special form is used to create templates.
define-infix-operator¶
The define-infix-operator special form is used to create reader
operators.
define-postfix-operator¶
The define-postfix-operator special form is used to create reader
operators.
define¶
The define special form is used to create lexically scoped
references between symbols, symbolic names, aka identifiers, and
values. It has an := synonym and a := reader operator.
define var value
:= var value
var := value
The base form of define is define var value and
creates a reference from var to value.
A second form is for defining functions: define (name
formals) body.
This is rewritten into the base form as: define name
(function/name name formals body) thus creating a reference
from name to a function value.
:*¶
The :* special form is used to create dynamically scoped
references between symbols, symbolic names, aka identifiers, and
values which will subsequently become environment variables when an
external command is executed. It has a :* reader operator.
:* var value
var :* value
environ-let¶
The environ-let special form is used to evaluate an expression in
the context of a dynamically scoped environment variable.
environ-let (var expr) body
environ-unset¶
The environ-unset special form is used to evaluate an expression
in the context of the absence of a dynamically scoped environment
variable.
environ-unset var body
:~¶
The :~ special form is used to create dynamically scoped
references between symbols, symbolic names, aka identifiers, and
values. It has a :~ reader operator.
:~ var value
var :~ value
dynamic¶
The dynamic special form is used to access dynamically scoped
variables.
There is normally no need to use this as the evaluator should figure our the variable is referencing a dynamic value and create the code accordingly.
dynamic-let¶
The dynamic-let special form is used to evaluate an expression in
the context of a dynamically scoped variable.
dynamic-let (var expr) body
dynamic-unset¶
The dynamic-unset special form is used to evaluate an expression
in the context of the absence of a dynamically scoped variable.
dynamic-unset var body
:$¶
The :$ special form is used to create lexically scoped references
between symbols, symbolic names, aka identifiers, and computed values.
It has a :$ reader operator.
:$ var getter
:$ var getter setter
:$ var #n setter
var :$ getter
var :$ getter setter
var :$ #n setter
Here, getter and setter are functions of no args and one arg, respectively, which retrieve or set some, usually, volatile value.
The value of variable SECONDS when evaluated returns the number of seconds the program has been running for. It has no associated setter so trying to give it a value is an error.
block¶
The block special form is largely a synonym for the begin sequencing special form but it does create a new
lexical context.
Variables created within a block are not accessible outside the block.
Amongst other things this allows for the creation of privately scoped variables.
trap¶
The trap special form is used to set in place a handler for a
condition type or types for the evaluation of some body.
trap condition handler body trap (conditions) handler body
Here, if a condition is raised during the execution of body that is one of the types in conditions or a descendent thereof then handler is run.
handler can choose to:
return a value on behalf of the erroring function by simply returning a value
can raise the condition to a previously established handler
See Condition Handlers for further information.
include¶
The include special form is used by the evaluator to pause,
load another file and then resume processing the current
file.
Note
The C defined include special form uses the C
primitive load function not any redefinition.
The Idio defined include special form simply opens the
file and evaluates each expression.
include filename
Last built at 2025-10-29T07:10:37Z+0000 from 3d9f9d3 (dev) for Idio 0.3.b.6