changeset 17:73170284e009

week 7 tutorial
author Markus Kaiser <markus.kaiser@in.tum.de>
date Fri, 30 Nov 2012 15:18:33 +0100
parents 7acf82c8fb3a
children a899535b1674
files exercises/src/Exercise_7.hs
diffstat 1 files changed, 133 insertions(+), 21 deletions(-) [+]
line wrap: on
line diff
--- a/exercises/src/Exercise_7.hs	Wed Nov 28 22:42:29 2012 +0100
+++ b/exercises/src/Exercise_7.hs	Fri Nov 30 15:18:33 2012 +0100
@@ -10,15 +10,21 @@
   Node a (Tree a) (Tree a)
     deriving (Eq, Show)
 
+tree =  (Node 4
+         (Node 2 (Node 1 Empty Empty) (Node 3 Empty Empty))
+         (Node 6 (Node 5 Empty Empty) (Node 7 Empty Empty)))
+
+insert :: Ord a => a -> Tree a -> Tree a
+insert x Empty = Node x Empty Empty
+insert x (Node a l r)
+        | x < a = Node a (insert x l) r
+        | a < x = Node a l (insert x r)
+        | otherwise = Node a l r
+
 data Html =
   Text String |
   Block String [Html]
 
-swissLetters :: [(Int, String)]
-swissLetters =
-  [(196, "Auml"), (214, "Ouml"), (220, "Uuml"),
-   (228, "auml"), (246, "ouml"), (252, "uuml")]
-
 grueezi =
   Block "html"
     [Block "head"
@@ -29,6 +35,19 @@
        [Block "h1" [Text "Gr\252ezi!"],
         Block "p" [Text "\196b\228, genau. Sal\252. Bis sp\246ter!"]]]
 
+kleiner =
+  Block "html"
+    [Block "a"
+        [Text "Hallo"],
+     Block "b"
+        [Text "du da!"]
+    ]
+
+swissLetters :: [(Int, String)]
+swissLetters =
+  [(196, "Auml"), (214, "Ouml"), (220, "Uuml"),
+   (228, "auml"), (246, "ouml"), (252, "uuml")]
+
 data DirTree a =
   File a |
   Dir a [DirTree a]
@@ -46,7 +65,10 @@
 
 {- 1. -}
 data WildChar =
-  Missing
+  AnyChar |
+  AnyString |
+  RawChar Char |
+  AnyCharIn [Char]
 
 
 data WildPat =
@@ -55,11 +77,14 @@
 
 {- 2. -}
 stringFromWildChar :: WildChar -> String
-stringFromWildChar = undefined
+stringFromWildChar AnyChar        = "?"
+stringFromWildChar AnyString      = "*"
+stringFromWildChar (RawChar c)    = [c]
+stringFromWildChar (AnyCharIn cs) = "[" ++ cs ++ "]"
 
 
 stringFromWildPat :: WildPat -> String
-stringFromWildPat (WildPat ws) = undefined
+stringFromWildPat (WildPat ws) = concatMap stringFromWildChar ws
 
 
 {- 3. -}
@@ -72,16 +97,61 @@
 
 {- 4. -}
 wildCharsFromString :: String -> [WildChar]
-wildCharsFromString = undefined
+wildCharsFromString [] = []
+wildCharsFromString (c : cs)
+        | c == '?' = AnyChar : ps
+        | c == '*' = AnyString : ps
+        | c == '[' =
+                case dropWhile (/= ']') cs of
+                []       -> RawChar '[' : ps
+                _ : rest -> AnyCharIn (takeWhile (/= ']') cs) :
+                                wildCharsFromString rest
+        | otherwise = RawChar c : ps
+        where ps = wildCharsFromString cs
 
 wildPatFromString :: String -> WildPat
 wildPatFromString cs = WildPat (wildCharsFromString cs)
 
 
 {- 5. -}
-prop_stringFromWildPatFromString s = undefined
+-- WildChar und WildPat QuickCheckkompatibel machen
+instance Eq WildChar where
+  RawChar c == RawChar c' = c == c'
+  AnyChar == AnyChar = True
+  AnyString == AnyString = True
+  AnyCharIn cs == AnyCharIn cs' = cs == cs'
+  _ == _ = False
+
+instance Eq WildPat where
+  WildPat p == WildPat p' = p == p'
+
+instance Arbitrary WildChar where
+  arbitrary =
+    oneof (map return
+      (map RawChar "abc?*[]" ++
+       [AnyChar, AnyString] ++
+       map AnyCharIn ["", "a", "bc", "bbc", "[]", "*?"]))
 
-prop_wildPatFromStringFromWildPat p = undefined
+instance Arbitrary WildPat where
+  arbitrary =
+    do ws <- arbitrary
+       return $ WildPat ws
+
+metas = "?*[]"
+
+isWildCharSafe (RawChar c) = c `notElem` metas
+isWildCharSafe (AnyCharIn cs) = all (`notElem` metas) cs
+isWildCharSafe _ = True
+
+isWildPatSafe (WildPat ws) = all isWildCharSafe ws
+
+-- Properties
+
+prop_stringFromWildPatFromString s =
+  stringFromWildPat (wildPatFromString s) == s
+
+prop_wildPatFromStringFromWildPat p =
+  isWildPatSafe p ==> wildPatFromString (stringFromWildPat p) == p
 
 
 {- 6. -}
@@ -97,37 +167,79 @@
 -}
 
 matchWildChars :: [WildChar] -> String -> Bool
-matchWildChars = undefined
+matchWildChars [] ys                      = null ys
+matchWildChars (AnyChar:ps) (y:ys)        = matchWildChars ps ys
+matchWildChars (AnyString:ps) []          = matchWildChars ps []
+matchWildChars (AnyString:ps) (y:ys)      = matchWildChars ps (y:ys)
+                                             || matchWildChars (AnyString:ps) ys
+matchWildChars ((AnyCharIn cs):ps) (y:ys) = elem y cs && matchWildChars ps ys
+matchWildChars ((RawChar c):ps) (y:ys)    = c == y && matchWildChars ps ys
+matchWildChars ps []                      = False
 
 
 matchWildPat :: WildPat -> String -> Bool
 matchWildPat (WildPat ws) = matchWildChars ws
 
-match = matchWildPat . wildPatFromString
+match ps ms = matchWildPat (wildPatFromString ps) ms
 
 
 
 {---------------------------------------------------------------------}
 {- Aufgabe G7.2 -}
 
-insert :: Ord a => a -> Tree a -> Tree a
-insert x Empty = Node x Empty Empty
-insert x (Node a l r)
-        | x < a = Node a (insert x l) r
-        | a < x = Node a l (insert x r)
-        | otherwise = Node a l r
+-- Beispiel für Rekursion über einen binären Suchbaum
+smallest :: Ord a => Tree a -> Maybe a
+smallest Empty            = Nothing
+smallest (Node v Empty _) = Just v
+smallest (Node _ l _)     = smallest l
+
+---
+
+listToSortedTree :: Ord a => [a] -> Tree a
+--listToSortedTree xs = foldl (\tree x -> insert x tree) Empty xs
+listToSortedTree xs = foldl (flip insert) Empty xs
+
+
+inorder :: Ord a => Tree a -> [a]
+inorder Empty        = []
+inorder (Node v l r) = inorder l ++ [v] ++ inorder r
 
 
 treeSort :: Ord a => [a] -> [a]
-treeSort = undefined
+treeSort = inorder . listToSortedTree
+
+---
 
+-- Properties
+-- treeSort sortiert
+prop_treeSort_isSorted ps =
+        let ts = treeSort ps in ts == sort ts
+
+-- treeSort entfernt keine Elemente
+prop_treeSort_isComplete ps =
+        eqSet (nub ps) (treeSort ps)
+        where
+        eqSet xs ys = null (xs \\ ys) && null (ys \\ xs)
 
 
 {---------------------------------------------------------------------}
 {- Aufgabe G7.3 -}
 
+htmlChar :: Char -> String
+htmlChar c
+        | o < 128 = [c]
+        | otherwise = "&" ++ entity ++ ";"
+        where
+        o = ord c
+        entity =
+                case lookup o swissLetters of
+                        Nothing ->   show o
+                        Just name -> name
+
+
 plainHtml :: Html -> String
-plainHtml = undefined
+plainHtml (Text cs)       = concatMap htmlChar cs
+plainHtml (Block name bs) = "<" ++ name ++ ">" ++ concatMap plainHtml bs ++ "</" ++ name ++ ">"