In the directory tests
you can find some files that provide example declarations for the different modes. They might offer a quick overview about the syntax of s, f, fw, cc, r, rg, un
. The following will give you an overview of the syntax starting with S. For all the other calculi only the extensions are explained.
Expression | Syntax | Note
|
---|---|---|
\x:E1.E2 |
abstraction
|
|
pi X:E1.E2 |
quantification | |
E1->E2 |
type, abbreviation for
|
|
mu X.E |
built-in iso-recursive types
|
|
E1 E2 |
application
|
|
fold E1 E2 |
folds the iso-recursive type of E2 once according to E1
|
|
unfold E1 E2 |
unfolds the iso-recursive type E1 of E2 once
|
|
x |
identifier
|
|
~12+3**(5-4) |
built-in integers and all available arithmetic operations on them
|
|
3=3 |
comparison on integers, | |
further operators are <<,<=, >>, >=, <> (unequal)
|
||
true and false |
boolean values |
|
not E |
negation of boolean values
|
|
unit |
unit value
|
|
Int, Bool, Unit |
built-in base types
|
|
if E1 then E2 else E3 |
conditional
|
|
E1 as E2 |
ascription; both expressions must be atomic
|
|
{x=E1,y=E2} |
records |
|
record@field |
record projection |
|
{x:E1,y:E2} |
record types
|
|
<x=E1> as E2 |
variant
|
|
<x:E1,y:e2> |
variant types
|
|
case E of <l1=x1> => E1 | ... | <ln=xn> => En |
case construct to access a value inside a variant; due to the uniform syntax you have to put parentheses around E,...,E except for atomic and arithmetic expressions.
|
|
ref E |
creates a reference for E
|
|
!E |
dereferences E
|
|
E1 := E2 |
assignment
|
|
let x=E1 in E2 |
let expression, but only terms can be bound |
Be aware of the operator for multiplication **
, the smaller test <<
and the greater test >>
that are somewhat unconventional. In S,F and Fw records and variants can only contain terms. Moreover a label cannot be used more than once in the same expression.
An expression sequence (E1;...;En)
is available as syntactic sugar. The sequence (E1;E2)
is transformed into an application (\x:Unit.E2) E1
. Therefore type errors in a sequence might be a bit inconvenient. A expression sequence is useful when you are working with references.
Expression | Syntax | Note |
---|---|---|
\X.E |
type abstraction | |
\/X.E |
the type of a type abstraction | |
(abbreviation for ) |
Expression | Syntax | Note |
---|---|---|
* |
base kind | |
\x:E1.E2 |
might be a kind like | |
\/X:E1.E2 |
might be a kind like |
if
and case
can be used on type level, i.e. you can write things like if E then Int else Bool
. Records and variants can
contain both terms and types at the same time.
There is a syntactic sugared version of , namely
.
Expression | Syntax | Note |
---|---|---|
\x.E2 |
blank lambda abstraction | |
.E | \f:'a->'b.E |
use of free type variables |
Do not confuse the blank lambda abstraction with the abbreviation in F, Fw and CC or the abstraction in untyped mode. There is the possibility to annotate a term with free type variables and all types from S mode. Therefore the expression \x.E
can be seen as an abbreviation for \x:'a.E
where 'a
is not used in the enclosing context.
This mode does not offer the full functionality of the previous ones. It consists of the basic elements which are lambda abstraction, application and variables. Additionally all basic types, terms and operations are integrated, i.e. numbers, boolean, unit, +,-, if-expression, ... . Records are also available. However be aware that these are different from the other constructs in an important way: the constraint typing algorithm may fail if there is a wrong projection.
As a challenge you can try to implement further constructs. Variants are for example very similar to records.
- \x. x x; > def it = <fun> : (mu A.A->'a)->'a
In the other respects the mode is just the same as R (but records are not available).
Iso-recursive types, let expressions, records, variants and references are not integrated into this mode.
In this mode the type checker and evaluator are set to the user's implementation. The user may implement the functions in UserCheckEval.sml. You can find explanation and an example implementation in this file in the directory src of the Cubint package.
This mode provides subtyping for variants and records and can be enabled in the typing modes s,f,fw and cc. There is no Top type integrated in the calculus. Therefore the interpreter does not accept input like if true then 3 else true
as a value of type Top is not very valuable. In subtyping mode you can leave out the variant ascription.
Christian Müller 2004-11-09