(* signature integer = sig type num; val makenum : int list -> num; val add : num * num -> num; val sub : num * num -> num; val mult : num * num -> num; exception suberror; end; *) structure big = struct datatype num = number of int list; exception suberror; fun makenum(a) = number(a); fun reverse(ls) = let fun reviter([],rev) = rev | reviter(x::ls,rev) = reviter(ls,x::rev) in reviter(ls,[]) end; fun addhelper([],[],carry) = if carry=0 then [] else [carry] | addhelper(a,[],carry) = addhelper(a,[carry],0) | addhelper([],b,carry) = addhelper(b,[carry],0) | addhelper(x::a,y::b,carry) = let val sum = x+y+carry in (sum mod 10)::addhelper(a,b,sum div 10) end; fun add(number(a),number(b)) = let val res = addhelper(reverse(a),reverse(b),0) in number(reverse(res)) end; fun subhelper([],[],borrow) = if borrow=0 then [] else raise suberror | subhelper([],x::b,borrow) = raise suberror | subhelper(x::a,[],borrow) = subhelper(x::a,[borrow],0) | subhelper(x::a,y::b,borrow) = let val z = x - borrow in if z >= y then (z-y)::subhelper(a,b,0) else (10+z-y)::subhelper(a,b,1) end; fun rmzeros([]) = [] | rmzeros([x]) = [x] | rmzeros(x::ls) = if x = 0 then rmzeros(ls) else x::ls; fun sub(number(a),number(b)) = let val res = subhelper(reverse(a),reverse(b),0) in number(rmzeros(reverse(res))) end; fun multdigit([],d,carry) = if carry=0 then [] else [carry] | multdigit(x::ls,d,carry) = if d=0 then [0] else let val sum = x*d+carry in (sum mod 10)::multdigit(ls,d,sum div 10) end; fun shift(k,ls) = if k = 0 then ls else 0::shift(k-1,ls); fun multhelper(a,[],k,result) = result | multhelper(a,x::b,k,result)= let val s = multdigit(a,x,0) val t = addhelper(result,shift(k,s),0) in multhelper(a,b,k+1,t) end; fun mult(number(a),number(b)) = let val res = multhelper(reverse(a),reverse(b),0,[]) in number(reverse(res)) end; end;