0size returns positive valuesavghead and tail are Safefoldr1averagemapinitinit'insertLists ElementsListmax type (I)max type (II)max type (III)max typekeysMapevalcreateunsafeTakeunpackchop
We've all been bitten by these!
ghci> :m +Data.Map
ghci> let m = fromList [ ("haskell" , "lazy")
, ("javascript", "eager")]
ghci> m ! "haskell"
"lazy"
ghci> m ! "python"
*** Exception: key is not in the map
Next, lets see how to use:
Sets to create safe associative maps
Measures to create well-scoped evaluators
Lets start with the type definition:
We will banish unpleasant exceptions of the form:
*** Exception: key is not in the map ***
By tracking the set of defined keys in the API
keys :: Map k v -> Set k
empty :: {m:Map k v | Set_emp (keys m)}
insert :: k:k -> v -> m:Map k v -> {m': Map k v | keys m' = add k m}
lookup :: k:k -> {m: Map | has k m} -> v
keysVia a measure similar to elems of a List:
MapThe empty map has no keys
Inserting a New Key-Value Binding ---------------------------------
Adds the key to those of the old Map
Q: Urgh! How can we prevent the impossible from happening?
Errors caught at compile time!
Well-Scoped Evaluators ======================
Lets define a small language of Expr
We can define values as a refinement of Expr
Q: What's a suitable signature for plus?
An Environment maps Variables to Values
We can now eval an Expr as:
Yikes! lookup is rejected!
How to ensure that Var is in Env?
eval looks-up Env for values of free variables
For example in let x = 10 in x + y
y occurs free,x occurs bound.ghci> let e1 = Let (V "x") (Val 10)
(Plus (Var (V "x")) (Var (V "y")))
ghci> free e1
fromList [V "y"]
e is well-scoped in an env G if free variables of e are defined in G:
evalQ: Can you go back and fix the type of eval so it is safe?
A closed Expr can be evaluated in an empty environment.
Q: Fix the definition of closed so topEval is safe?
safeEval should work with any Expr and Env
Q: What is the right check ok such that safeEval verifies?
Next: Case Studies
CHEAT SHEET :)
topEval
topEval: closed e = free e == S.empty
safeEval: ok = wellScoped g e
closed e = free e == S.empty has k m = k S.member keys m ok = wellScoped g e