annotate exercises/src/SetPairList.hs @ 26:ce9610f08925

Merge
author Markus Kaiser <markus.kaiser@in.tum.de>
date Wed, 09 Jan 2013 19:45:47 +0100
parents 34fea195e238 ea3fba2381bc
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
1 module SetPairList(Set, empty, insert, isin, size, union, delete) where
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
2
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
3 -- Abstraction function
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
4 {-
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
5 alpha :: Set a -> {a}
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
6 alpha (S []) = {}
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
7 alpha (S ((a, b):xs)) = {a..b} union (alpha xs)
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
8
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
9 To show: (10 things)
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
10 alpha empty = {}
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
11 invar s ==> alpha (insert x s) = {x} union alpha s
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
12 invar s ==> alpha (delete x s) = alpha s \ {x}
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
13 invar s ==> isin x s = x \in alpha s
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
14 invar s ==> size s = |alpha s|
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
15 invar s1, invar s2 ==> alpha (union s1 s2) = (alpha s1) union (alpha s2)
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
16
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
17 invar empty
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
18 invar s ==> invar (insert x s)
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
19 invar s ==> invar(delete x s)
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
20 invar s1, invar s2 ==> invar (union s1 s2)
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
21 -}
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
22
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
23 -- Interface
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
24 newtype Set a = S (PairList a)
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
25
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
26 invar :: Integral a => Set a -> Bool
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
27 invar (S s) = invarPL s
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
28
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
29 empty :: Set a
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
30 empty = S emptyPL
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
31
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
32 insert :: Integral a => a -> Set a -> Set a
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
33 insert n (S s) = S (insertPL n s)
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
34
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
35 isin :: Integral a => a -> Set a -> Bool
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
36 isin n (S s) = isinPL n s
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
37
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
38 size :: Integral a => Set a -> Integer
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
39 size (S s) = sizePL s
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
40
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
41 union :: Integral a => Set a -> Set a -> Set a
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
42 union (S s1) (S s2) = S (unionPL s1 s2)
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
43
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
44 delete :: Integral a => a -> Set a -> Set a
25
ea3fba2381bc week 10 tutorial
Markus Kaiser <markus.kaiser@in.tum.de>
parents: 23
diff changeset
45 delete n (S s) = S (deletePL n s)
23
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
46
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
47 -- Implementation
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
48 type PairList a = [(a, a)]
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
49
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
50 invarPL :: Integral a => PairList a -> Bool
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
51 invarPL [] = True
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
52 invarPL [(m,n)] = m <= n
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
53 invarPL ((m1,n1):(m2,n2):ms) =
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
54 m1 <= n1 && n1 + 1 < m2 && invarPL ((m2,n2):ms)
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
55
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
56 emptyPL :: PairList a
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
57 emptyPL = []
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
58
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
59 insertPL :: Integral a => a -> PairList a -> PairList a
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
60 insertPL n [] = [(n,n)]
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
61 insertPL n ((k1,l1) : (k2,l2) : ks)
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
62 | l1 + 1 == n && n + 1 == k2 = (k1,l2) : ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
63 insertPL n ((k,l) : ks)
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
64 | n + 1 == k = (n,l) : ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
65 | n < k = (n,n) : (k,l) : ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
66 | k <= n && n <= l = (k,l) : ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
67 | l + 1 == n = (k,n) : ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
68 | otherwise = (k,l) : insertPL n ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
69
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
70 isinPL :: Ord a => a -> PairList a -> Bool
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
71 isinPL n = any (\(k,l) -> k <= n && n <= l)
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
72
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
73 sizePL :: Integral a => PairList a -> Integer
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
74 sizePL [] = 0
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
75 sizePL ((k,l) : s) = toInteger (l - k + 1) + sizePL s
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
76
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
77 unionPL :: Integral a => PairList a -> PairList a -> PairList a
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
78 unionPL [] ls = ls
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
79 unionPL ks [] = ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
80 unionPL ((k1,l1):ks) ((k2,l2):ls) =
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
81 if k1 <= k2
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
82 then if l1 + 1 < k2 then (k1,l1) : unionPL ks ((k2, l2):ls)
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
83 else if l1 <= l2 then unionPL ks ((k1,l2):ls)
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
84 else {- l1 > l2 -} unionPL ((k1,l1):ks) ls
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
85 else if k1 <= l2 + 1
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
86 then if l1 <= l2 then unionPL ks ((k2,l2):ls)
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
87 else {- l1 > l2 -} unionPL ((k2,l1):ks) ls
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
88 else (k2,l2) : unionPL ((k1,l1):ks) ls
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
89
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
90 deletePL :: Integral a => a -> PairList a -> PairList a
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
91 deletePL n [] = []
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
92 deletePL n ((k,l) : ks)
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
93 | n < k = (k,l) : ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
94 | n == k = if k < l then (k+1,l) : ks else ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
95 | k < n && n < l = (k,n-1) : (n+1,l) : ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
96 | n == l = if k < l then (k,l-1) : ks else ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
97 | otherwise = (k,l) : deletePL n ks
f9386825bf71 week 10
Markus Kaiser <markus.kaiser@in.tum.de>
parents:
diff changeset
98