Introduction to Programming using SML

Introduction to Programming using SML
Michael R. Hansen and Hans Rischel
Addison-Wesley 1999
ISBN 0-201-39820-6


Page 9, line 2 from bottom: f(3+1) div (3+1) should be: (f(3+1) div (3+1)) div 3

Page 10, line 12 from bottom: arguments should be: argument

Page 15, line 6 from bottom: operators and functions should be: functions

Page 16, last line: monadic minus. should be: negative sign and monadic minus.

Page 18, line 7-8: in Section D.1.6 should be: in Table D.4

Page 20, include just before Section 2.4.1:
We use the notation (e,env) to denote that the expression e is to be evaluated in the environment env. Such pairs (e,env) are used in evaluation steps as illustrated below. Note that the notation (e,env) is not part of SML but a meta notation used to explain the meaning of SML programs.

Page 22, line 6 from bottom: quences: should be: quences, cf. Table 2.2 (or Table F.2).

Page 26, bottom: add the following:
The terminating semicolon in e.g.
adjString "123"; 
is not a part of the expression, but it terminates the expression. The SML system will hence know that the value of the expression should be evaluated. A similar remark applies to terminating semicolons after declarations.

Page 35, line 12 from bottom: precedence and association should be: association and precedence

Page 45, line 9: The evaluation of...
should be:

Note that there must not be a semicolon after `val d = b*b-4.0*a*c' as the declaration is a part of the let-expression.
The evaluation of...

Page 57, Table 4.7: canc(5,10) should be: mkQ(5,10) and: canc(~5,10) should be: mkQ(~5,10)

Page 61, line 2: Section D.4 should be: Table D.17

Page 68, line 10 from bottom: spliting should be: splitting

Page 73, insert before line 10 from bottom:
The concat function joins a list of strings into one string, for example:
  concat ["today"," ","is", " Monday"];
  val it = "today is Monday" : string

Page 91, line 3 from bottom: for some real number ... The line should not be indented

Page 92, line 15 to 13 from bottom: Note that the brackets ... These three lines contains an important remark and should be placed in a shaded remark box.

Page 97, line 19: NONE as n is greater than zero. should be: NONE as n > 0 and hence (n-1) >= 0.

Page 101, line 14: i.e. there are more rows to try. should be: i.e. there are more rows to try in column x.

Page 127, line 3 - 5 should be replaced by:
the declarations in Section 4.2.2, except that the internal representation for
rational numbers are now trees of the form: mkQ(a,b).

Page 127, line 13 - 28 (fun ++...) should be replaced by:
   infix 6 ++ -- 
   infix 7 ** //
   infix 4 ==  ; 

   fun (MkQ(a,b)) ++ (MkQ(c,d)) = MkQ(a*d + b*c, b*d);
   fun (MkQ(a,b)) -- (MkQ(c,d)) = MkQ(a*d - b*c, b*d);            
   fun (MkQ(a,b)) ** (MkQ(c,d)) = MkQ(a*c, b*d);
   fun (MkQ(a,b)) // (MkQ(c,d)) = MkQ(a,b) ** mkQ(d,c);

   fun (MkQ(a,b)) == (MkQ(c,d)) = (a*d = b*c);

      fun gcd(0,n) = n              
        | gcd(m,n) = gcd(n mod m,m); 
      fun toString(MkQ(p,q)) = 
         let val sign = if p*q<0 then "~" else ""
             val ap = abs p
             val aq = abs q
             val d  = gcd(ap,aq)
         in sign ^ (Int.toString(ap div d)) 
                 ^ "/" ^ (Int.toString(aq div d))

Page 127, line 29 to bottom (abstype qnum...) should be replaced by:
  infix 6 ++
  infix 6 --
  infix 7 **
  infix 7 //
  infix 4 ==
  type qnum = qnum
  exn QDiv = QDiv : exn
  val mkQ = fn : int * int -> qnum
  val ++ = fn : qnum * qnum -> qnum
  val -- = fn : qnum * qnum -> qnum
  val ** = fn : qnum * qnum -> qnum
  val // = fn : qnum * qnum -> qnum
  val == = fn : qnum * qnum -> bool
  val toString = fn : qnum -> string

Page 128, line 9 - 12 (The operators...) should be removed.

Page 128, line 13 (and the declared...) should be replaced by:
The declared functions can be applied to values created using the mkQ function:

Page 138, line 3 from bottom: does have a binding for ... should be: does not have a binding for ...

Page 142, line 17-18 from bottom: Three occurences of argument of
should be replaced by
argument of the function

Page 153, line 4: bindings from the actual environment of those should be: bindings of those

Page 153, line 7 from bottom: where (env, x, e)is the should be: where (env, x, e) is the

Page 154, line 9 from bottom: Applying fn a = a + ten to should be: Applying fn a => a + ten to

Page 176, line 14: (which may be inconvenient) should be: (which may be inconvenient, see Section D.2 for a similar inconvenience of using open on the libraries Int and Real)

Page 207, line 15 from bottom: a illegal
should be:
an illegal

Page 210, line 5 from bottom: val newReg = Table.empty: prodReg
should be:
val newReg = Table.empty

Page 212, line 11-9 from bottom:
case Table.getval(pid,preg) of
    [] => [(pid,1)] 
  | pl => partsListBreakDown(pl,preg)
should be:
case Table.lookup(pid,preg) of
     SOME [] => [(pid,1)] 
   | SOME pl => partsListBreakDown(pl,preg)
   | NONE    => raise ProdReg 

Page 222, line 5: This is a test>val it = () : unit should be: This is a test val it = () : unit

Page 223, line 2: val it = false : bool should be: val it = false : bool

Page 227, top line: A list [e1,...,en] of values e1,...,en
should be: A list [v1,...,vn] of values v1,...,vn

Page 227, line 2: the value ek should be: the value vk

Page 229, exercise 14.4 (a):
fileFoldr: (string * 'a -> 'a) -> string -> 'a
should be:
fileFoldr: (string * 'a -> 'a) -> 'a -> string -> 'a

Page 229, exercise 14.4 (c):
fileFoldl: (string * 'a -> 'a) -> string -> 'a
should be:
fileFoldl: (string * 'a -> 'a) -> 'a -> string -> 'a

Page 235, line 6: dialogue would not stop if should be: dialogue would not get to a stop node if

Page 240, line 3: cf. the above remark 1 should be: cf. the above remark a

Page 240, line 5: cf. the above remark 2 should be: cf. the above remark b

Page 266, line 14-16:
ref pat matches the value v when v is a reference to a cell in the store containing a value x, such that the pattern pat matches the value x.
should be:
ref pat matches the value r when r is a reference to a cell in the store containing a value v, such that the pattern pat matches the value v.

Page 288, insert after line 5: A constructor is always written in nonfix form in a datatype or exeception declaration where the constructor is followed by "of" and the argument type (cf. the syntax class conbind in table B.6 on page 301). The "op" directive is optional in this case.

Page 289, line 9 from bottom: the reserved word * should be: the character *

Page 292, line 6: Figure B.1 (on Page 290) should be: Figure B.1 (on Page 289)

Page 293, line 1 should be indented.

Page 295, line 3 from bottom: A top level declaration of polymorphic type
should be:
A top level declaration of a value of polymorphic type

Page 322, line 14: From i'th to j'ih char should be: j chars from i'th

Page 322, line 8 from bottom: String.substring("abcd",1,2) = "bc"
should be:
String.substring("abcdef",2,3) = "cde"

Page 331, line 6: floor should be: ceil

Page 331, line 7: ceil should be: floor

Page 332, line 5: The string "false" or true should be: The string "false" or "true"

Page 334, line 15: time format commands should be: date format commands

Page 334, Table D.32: Format commands. should be: Date format commands.

Page 350, line 10: 'problem solving' should be: `problem solving'

Comments to:
Last update: April 15, 2004