Unformatted text preview:

342CS 538 Spring 2006©Structures and SignaturesIn C++ and Java you can groupvariable and function definitions intoclasses. In Java you can also groupclasses into packages.In ML you can group value, exceptionand function definitions intostructures.You can then import selecteddefinitions from the structure (usingthe notationstructure.name) oryou canopen the structure, therebyimporting all the definitions withinthe structure.(Examples used in this section may befound at~cs538-1/public/sml/struct.sml)343CS 538 Spring 2006©The general form of a structuredefinition isstructure name =struct val, exception and fun definitionsendFor example,structure Mapping =struct exception NotFound; val create = []; fun lookup(key,[]) = raise NotFound | lookup(key, (key1,value1)::rest) = if key = key1 then value1 else lookup(key,rest);344CS 538 Spring 2006© fun insert(key,value,[]) = [(key,value)] | insert(key,value, (key1,value1)::rest) = if key = key1 then (key,value)::rest else (key1,value1):: insert(key,value,rest);end;We can access members of thisstructure asMapping.name. ThusMapping.insert(538,"languages",[]);val it = [(538,"languages")] :(int * string) listopen Mapping;exception NotFoundval create : 'a listval insert : ''a * 'b * (''a * 'b) list -> (''a * 'b) listval lookup : ''a * (''a * 'b)list -> 'b345CS 538 Spring 2006©SignaturesEach structure has a signature, whichis it type.For example,Mapping’s signature isstructure Mapping : sig exception NotFound val create : 'a list val insert : ''a * 'b * (''a * 'b) list -> (''a * 'b) list val lookup : ''a * (''a * 'b) list -> 'b end346CS 538 Spring 2006©You can define a signature assignature name = sig type definitions for values, functions and exceptionsendFor example,signature Str2IntMapping =sig exception NotFound; val lookup:string * (string*int) list -> int;end;347CS 538 Spring 2006©Signatures can be used to• Restrict the type of a value orfunction in a structure.• Hide selected definitions that appearin a structureFor examplestructure Str2IntMap :Str2IntMapping = Mapping;defines a new structure, Str2IntMap,created by restrictingMapping to theStr2IntMapping signature. Whenwe do this we getopen Str2IntMap; exception NotFound val lookup : string * (string * int) list -> intOnly lookup and NotFound arecreated, andlookup is limited to keysthat are strings.348CS 538 Spring 2006©Extending ML’s PolymorphismIn languages like C++ and Java wemust use types likevoid* or Objectto simulate the polymorphism thatML provides. In ML whenever possiblea general type (a polytype) is usedrather than a fixed type. Thus infun len([]) = 0 | len(a::b) = 1 + len(b);we get a type of 'a list -> intbecause this is the most general typepossible that is consistent withlen’sdefinition.Is this form of polymorphism generalenough to capture the general idea ofmaking program definitions as type-independent as possible?349CS 538 Spring 2006©It isn’t, and to see why consider thefollowing ML definition of a mergesort. A merge sort operates by firstsplitting a list into two equal lengthsublists. The following function doesthis:fun split [] = ([],[]) | split [a] = ([a],[]) | split (a::b::rest) = let val (left,right) = split(rest) in (a::left, b::right) end;After the input list is split into twohalves, each half is recursively sorted,then the sorted halves are mergedtogether into a single list.The following ML function mergestwo sorted lists into one:350CS 538 Spring 2006©fun merge([],[]) = [] | merge([],hd::tl) = hd::tl | merge(hd::tl,[]) = hd::tl | merge(hd::tl,h::t) = if hd <= h then hd::merge(tl,h::t) else h::merge(hd::tl,t)With these two subroutines, adefinition of a sort is easy:fun sort [] = [] | sort([a]) = [a] | sort(a::b::rest) = let val (left,right) = split(a::b::rest) in merge(sort(left),sort(right)) end;351CS 538 Spring 2006©This definition looks very general—itshould work for a list of any type.Unfortunately, when ML types thefunctions we get a surprise:val split = fn : 'a list -> 'a list * 'a listval merge = fn : int list * int list -> int listval sort = fn : int list -> int listsplit is polymorphic, but merge andsort are limited to integer lists!Where did this restriction come from?352CS 538 Spring 2006©The problem is that we did acomparison inmerge using the <=operator, and ML typed this as aninteger comparison.We can make our definition of sortmore general by adding a comparisonfunction,le(a,b) as a parameter tomerge and sort. If we curry thisparameter we may be able to hide itfrom end users. Our updateddefinitions are:fun merge(le,[],[]) = [] | merge(le,[],hd::tl) = hd::tl | merge(le,hd::tl,[]) = hd::tl | merge(le,hd::tl,h::t) = if le(hd,h) then hd::merge(le,tl,h::t) else h::merge(le,hd::tl,t)353CS 538 Spring 2006©fun sort le [] = [] | sort le [a] = [a] | sort le (a::b::rest) = let val (left,right) = split(a::b::rest) in merge(le, sort le left,sort le right) end;Now the types of merge and sortare:val merge = fn : ('a * 'a -> bool) * 'a list * 'a list -> 'a listval sort = fn : ('a * 'a -> bool) -> 'a list -> 'a listWe can now “customize” sort bychoosing a particular definition forthele parameter:fun le(a,b) = a <= b;val le = fn : int * int -> bool354CS 538 Spring 2006©fun intsort L = sort le L;val intsort = fn : int list -> int listintsort( [4,9,0,2,111,~22,8,~123]);val it = [~123,~22,0,2,4,8,9,111]: int listfun strle(a:string,b) = a <= b;val strle = fn : string * string -> boolfun strsort L = sort strle L;val strsort =fn : string list -> string liststrsort( ["aac","aaa","ABC","123"]);val it =["123","ABC","aaa","aac"] :string list355CS 538 Spring 2006©Making the comparison relation anexplicit parameter works, but it is abit ugly and inefficient. Moreover, ifwe have several functions thatdepend on the comparison relation,we need to ensure that they all usethe same relation. Thus if we wish todefine a predicateinOrder that testsif a list is already sorted, we can use:fun inOrder le [] = true | inOrder le [a] = true | inOrder le (a::b::rest) = le(a,b) andalso inOrder le (b::rest);val inOrder = fn : ('a * 'a -> bool) -> 'a list -> boolNow sort and inOrder need to usethe same definition ofle. But howcan we enforce this?356CS 538 Spring 2006©The structure mechanism we studiedearlier


View Full Document

UW-Madison COMPSCI 538 - Lecture 25 Notes

Download Lecture 25 Notes
Our administrator received your request to download this document. We will send you the file to your email shortly.
Loading Unlocking...
Login

Join to view Lecture 25 Notes and access 3M+ class-specific study document.

or
We will never post anything without your permission.
Don't have an account?
Sign Up

Join to view Lecture 25 Notes 2 2 and access 3M+ class-specific study document.

or

By creating an account you agree to our Privacy Policy and Terms Of Use

Already a member?