Elements of ML Programming, 2nd Edition (ML97) |

fun cube(x:real) = x*x*x;

fun third(L) = hd(tl(tl(L)));

fun thirdChar(s) = third(explode(s));

fun minMax(a,b,c) = if a<b then if b<c then (a,c) else (* b is largest *) if a<c then (a,b) else (c,b) else (* a >= b *) if a<c then (b,c) else (* a is largest *) if b<c then (b,a) else (c,a);

fun fact(n) = if n<=1 then 1 else n*fact(n-1);

fun duplicate(L) = if L=nil then nil else hd(L)::hd(L)::duplicate(tl(L));

fun maxList(L: string list) = if tl(L)=nil (* L is a single element *) then hd(L) (* the single element is the maximum *) else (* assume there are at least 2 elements *) if hd(L)>hd(tl(L)) (* the first element exceeds the second *) then maxList(hd(L)::tl(tl(L))) (* eliminate second element *) else maxList(tl(L)) (* eliminate first element *);Download this program

There are considerably simpler ways to solve this problem if we use the let-construct described in Section 3.4.

fun fact(1) = 1 | fact(n) = n*fact(n-1);

fun duplicate(nil) = nil | duplicate(x::xs) = x::x::duplicate(xs);

fun maxList([x:real]) = x | maxList(x::y::zs) = if x<y then maxList(y::zs) else maxList(x::zs);

fun square(0) = 0 | square(n) = square(n-1)+2*n-1;

fun flip(nil) = nil | flip((x as (a:int,b))::xs) = if a<b then x::flip(xs) else (b,a)::flip(xs);

fun member(_,nil) = false | member(x,y::ys) = (x=y orelse member(x,ys));We might be tempted to replace the second line by

| member(x,x::xs) = true | member(x,_::xs) = member(x,xs);However, it is not permitted to use an identifier like

fun insert(x,nil) = [x] | insert(x,S as y::ys) = if x=y then S else y::insert(x,ys);

fun insertAll(a,nil) = nil | insertAll(a,L::Ls) = (a::L)::insertAll(a,Ls);The idea behind the second line is that we put

fun powerSet(nil) = [nil] | powerSet(x::xs) = powerSet(xs)@insertAll(x,powerSet(xs));The function above computes the power set as follows. For a basis, the power set of the empty set is the set containing the empty set. The latter is represented by the list

fun prodDiff1(_,nil) = 1.0 | prodDiff1(a,b::bs) = (a-b)*prodDiff1(a,bs); fun prodDiff(nil) = 1.0 | prodDiff(b::bs) = prodDiff1(b,bs)*prodDiff(bs);

fun emptyList(nil) = true | emptyList(_) = false;

fun thousandthPower(x:real) = let val x = x*x*x*x*x; val x = x*x*x*x*x; val x = x*x*x*x*x in x*x*x*x*x*x*x*x end;Download this program

fun powerSet(nil) = [nil] | powerSet(x::xs) = let val L = powerSet(xs) in L @ insertAll(x,L) end;Download the complete program

fun doubleExp(x:real,0) = x | doubleExp(x,i) = let val y = doubleExp(x,i-1) in y*y end;Note that we could have written the recursive case simply as

| doubleExp(x,i) = doubleExp(x,i-1) * doubleExp(x,i-1);However, it would take considerably more time to compute the function this way, as computations would then be repeated an exponential number of times.

fun cat(nil,M) = M | cat(x::xs,M) = x::cat(xs,M);That is, we recursively put the tail of

fun polyFromRoots(nil) = [1.0] | polyFromRoots(p::ps) = pmult([~p,1.0],polyFromRoots(ps));