#$K+CML Reference
	CML's built-in types
	Defining simple values and functions
	Predeclared Values and Constructors
	Defining types
	Exceptions and handling them
	Error Messages

#$K+CML's Types
What is a type? It is simply a set of values which can be treated uniformly by CML under all circumstances. For instance the whole number 1 is of type int and so is any other whole number. Any expression that evaluates to an integer also has type int.
CML supports a variety of types as standard and in addition you can define your own types. This section catalogs the built-in types and values.
The Booleans
Unlike in BASIC or C truth values have their own type in CML. The values are true and false and they have type bool. They are returned by the relational operators (<, <=, =, <>, >= and >) are used in conditional expressions.
The function not, the operators andalso and orelse and the conditional expression if ... then ... else ... are provided.
not is boolean negation and has type bool -> bool; not true is false and vice versa.
andalso is boolean conjunction; it is not quite an ordinary infix operator but is used just like one. abc andalso def is true if both abc and def are true, otherwise it is false. CML evaluates abc first and only if it is true does it need to evaluate def.
orelse is boolean disjunction. abc orelse def is false if both abc and def are false, otherwise it is true. Again CML will only evaluate def if it has to.
Given three expressions abc, def and ghi, the form if abc then def else ghi is another expression, however, abc must have type bool and the other two expressions must be of the same type which is then the type of the overall expression. CML evaulates the expression as follows: firstly it evaluates abc, if this is true then the result is had by evaluating def, if it is false then the result is had by evaulating ghi.
Try out the following examples:
2 = 3;
true = true;
true = false;
if true then 13 else 24;
false andalso (1.0/0.0 = 18.0);
if (if 2+2=4 then true else false) then 2+2=5 else 2+3=5;
The Integers
These are your basic whole numbers, both positive and negative. Every whole number belongs to the type int. CML can handle rather large integers, just try typing in a very large number (and a semicolon), it won't faze CML. Now try:
it * it;
This gives the square of the number you just entered. * is the multiplication operator. The operators + and - perform addition and subtraction respectively. Division on the integers is done with the operator div which has a companion operator mod.
How about negative numbers? The minus sign "-" is a subtraction operator (taking two arguments) and cannot be used as a negation prefix, use "~" instead: try ~2 + 3;.
You can use all the comparison operators (<= etc) on the integers. Here is an example function which takes two integer arguments and returns another integer. See if you can work out what it does:
fun puzzle (x,y) = if x < y
       then if x = 0 then y else puzzle (x,y-x)
       else puzzle (y,x-y);
Does it work for negative arguments?
Tuples
In CML you can build composite values using parentheses and commas. So the pair (1,true) is a new value which packages 1 and true together. In general, given a of type t and b of type s the pair (a,b) has type s * t.
You can also make tuples of any size bigger than two; quintuples (and so on) are fine and have corresponding large types. There is also a special zero-tuple, (). This has type unit and is normally called unit itself.
Floating point numbers
In any programming language these are some approximation to the real numbers and CML the type of these numbers is real.
To have CML recognise a number as a real rather than an int it must have at least one of:
	a decimal point in the number
	a trailing exponent consisting of the letter E followed by a (possibly negated) integer.

These are valid floating point numbers: 2.3, 3E4, ~2E~6, 2.0E2.
All the relational (comparison) operators can be used on values of type real as well as the operators +, -, * and /. The negation operator is ~, the same as for integers.
These functions are also provided:
	abs : real -> real - absolute value
	sqrt : real -> real - square root :real -> real
	sin : real -> real - sine
	cos : real -> real - cosine
	arctan : real -> real - inverse tangent
	exp : real -> real - exponentiation (base e)
	ln : real -> real - natural logarithm (base e)
	floor : real -> int - floating point to integer conversion (rounding towards negative infinity)
	real : int -> real - integer to floating point conversion

Strings
Strings are sequences of characters, written between double quotes. "string one", "" and "the previous string was empty" are two example values of type string.
The type string is a peculiarity of ML. Most functional languages have some type of characters and define strings simply as lists (see below) of characters. ML has no separate type for characters, though you could use ints as a substitute.
All the comparison operators can be used on strings; in addition ^ is the string concatenation (joining) operator. The function size : string -> int yields the number of characters in a string.
The function chr : int -> string converts an integer n in the range 0 to 255 into a string of length 1 consisting of the single character with character value n.
The function ord : string -> int does the reverse thing; to be precise, given a non-empty string it returns the character value of the first element of the string.
implode takes a list of strings and returns their concatenation. explode turns a string into a list of single character strings. They allow you define string processing functions in term of list processing functions.
Lists
Lists are sequences of values where all the values in a list must have the same type.

#$K+Defining simple values and functions
Declarations are phrases that effect the environment enabling values to be bound to names. A simple use is val a = 7; which binds a to the value 7, you can then type a; and ML will respond with something like 7 : int. Defining functions using fun is an example of a declaration. Declarations can be to create variables, functions, types, datatypes, and exceptions.
Some of the following declarations below are deliberately presented in a restricted form, see "Standard ML" (Harper, MacQueen, Milner) for in-depth details.
val
val <pattern> = <expression>
Used to give a value a name. Examples are
val a = "Hot Dogs";      (* gives a the string value "Hot Dogs" *)
val b::c = [1,2,3,4];    (* gives b the value 1, c the value [2,3,4] *)
Notice that patterns can be used with contructors as in the second example above.
fun
fun <name> <pat11> ... <pat1n> = exp1
  |
...
  | <name> <patm1> ... <patmn> = expm
Declares a function. Simple use is fun addone x = x+1; which defines the function addone (which has the effefct of adding one to an integer). Slightly more complex use involving pattern matching might be
fun map f nil = nil
  | map f (x::x') = f x :: map f x';
which defines the familiar map function.
type
type <name> = <type>
Declares an abbreviation for an existing type. If you had a vector manipulation package, you might want something like type vector = real*real to define a two-dimensional vector type for example.
datatype
datatype <type-variable-list> <constructor> =
<con1> of <type1> | ... | <conn> of <typen>
Datatypes are used to declare new types (or type constructors). The name of the new type is introduced on the left, and the possible constructions the type are on the right. Paulson gives the following example:
datatype person = King
                | Peer of string*string*int
                | Knight of string
                | Peasant of string;
This declares the type person, and four constructors (King, Peer, Knight, Peasant). Notice that King is a nullary type constructor, hence there is only one King. The constructors can be used to create values of type person as in Peer("Duke","Norfolk",9), creating the 9th Duke of Norfolk. They can also be used in pattern matches:
fun title King               = "His Majesty the King"
  | title (Peer(deg,terr,_)) = "The " ^ deg ^ " of " ^ terr
  | title (Knight name)      = "Sir " ^ name
  | title (Peasant name)     = name;
exception
exception name [of <type>]
Declares an exception. An exception is used in conjunction with handle and raise forms to perform non-local exit from an expression. Perhaps you should see the topic on exceptions and handling them.

#$K+Predeclared Variables and Constructors
In the following list, the type "num" stands for either int or real, "nums" stands for integer, real, or string. "ty" stands for an arbitrary type, "mty" stands for any monotype, "ety" stands for any equality type.
Nonfix Values
nil : 'a list
	Type constructor for the empty list.
map : ('a -> 'b) -> 'a list -> 'b list
	The map function takes a function and returns a function that applies the function to every element of a list.
rev : 'a list -> 'a list
	Reverses a list.
true, false : bool
	The two boolean constructors.
not : bool -> bool
	The logical not operator.
~ : num -> num
	Unary minus for integers and reals.
abs : num -> num
	Returns the absolute value of a number.
floor : real -> int
	The floor of a number is defined to be the greatest integer no bigger than it.
real : int -> real
	Converts an integer into a floating point number.
sin, cos, arctan : real -> real
	The mathematical functions of the same name. All three work in radians not degrees.
exp, ln : real -> real
	Exponentiation and logarithms in the natural base (e).
size : string -> int
	Returns the length of a string (which is the number of characters in it).
chr : int -> string
	Converts an integer into a one character string represented by that number. A bit hacky really.
ord : string -> int
	Takes a string and returns the integer representing the first character of that string. ord (chr n) = n.
explode : string -> string list
	Takes a string and returns a list of one-character strings.
implode : string list -> string
	Takes a list of one-character strings and joins them all together to form a single string. Implode and explode are inverse.
ref : mty -> mty ref
	Creates a reference containing a value.
! : 'a ref -> 'a
	Returns the contents of a reference.
print : ty -> ty
	Prints out a value. Extremely imperative.
makestring : ty -> string
	Returns the string that would be printed if you used print to print out the value.

Infix Values
Precedence 7
/ : real * real -> real
	Division on real numbers.
div : int * int -> int
	Integer division.
mod : int * int -> int
	Returns its first argument modulo the second. The result has the same sign as the second argument.
* : num * num -> num
	Multiplication on integers or reals.

Precedence 6
+ : num * num -> num
	Addition; what did you expect?
- : num * num -> num
	The first argument is the subtrahend, the second is the subtractor.
^ : string * string -> string
	Returns the concatenation of two strings.

Precedence 5
:: : 'a * 'a list -> 'a list
	The cons operator for building lists.
@ : 'a list * 'a list -> 'a list
	The append operator, returns the concatenation of the two lists.

Precedence 4
= : ety * ety -> bool
	The equality relation.
<> : ety * ety -> bool
	Test for not-equal.
< : nums * nums -> bool
	The standard ordering for numbers, and lexical comparison for strings.
> : nums * nums -> bool
	a > b iff b < a.
<= : nums * nums -> bool
	Less than or equal to.
>= : nums * nums -> bool
	Greater than or equal to.

Precedence 3
o : ('b -> 'c) * ('a -> 'b) -> ('a -> 'c)
	Performs function composition. So f o g returns the function that is the composition of f and g.
:= : mty ref * mty -> unit
	Assignment.

Notes
All binary operators except cons (::) associate to the left with other operators of the same precedence. Cons (::) is right associative.

#$K+Defining types
New types can be introduced using the constructions "type", "dattype" and "abstype". This last is in many respects similar to datatype, but arranges to encapsulate the type so that most users have no access to its internal structure. It is not documented further in this help text.

#$K+Exceptions and handling them
New exceptions can be introduced using the "exception" declaration. If smash is the name of such an exception, raise smash activates it. The operator handle may be used to allow programs to trap and recover from exceptions. More details will be given in the lectures or books.

#$K+Error messages
Many of the error messages generated by CML and cryptic and unhelpful. The main resonse to seeing one that you should have is to re-read and double-check your code. The system insists that you get all types in your program utterly consistent, and that you never refer to any function or value that has not already been defined. If in doubt you can COPY your output including both what you typed and the error messages you got and PASTE it into a notepad, from where you can print a copy to take to your supervisor or a demonstrator for further assistence.