Technische Universität Braunschweig Institut für Programmierung und Reaktive Systeme Dr. Werner Struckmann 24. November 2011 Programmieren für Fortgeschrittene 3. Übungsblatt Aufgabe 7: a) Geben Sie eine Funktion an, mit der die Fakultät einer ganzen positiven Zahl n berechnet werden kann (den Typen Integer anstelle von Int verwenden). b) Geben Sie eine Funktion an, die für die beiden Argumente c::Char und n::Int eine Zeichenkette der Länge n ausgibt, welche nur aus Wiederholungen des Buchstaben c besteht. c) Erweitern Sie die partielle Funktion natSum (Listing 3.1) zu einer totalen Funktion über dem Datentypen Int. Geben Sie in vorher undefinierten Fällen eine Fehlermeldung durch die Funktion error aus. d) Setzen Sie die iterative Variante des euklidischen Algorithmus zur Bestimmung des größten gemeinsamen Teilers in eine funktionale Implementierung in Haskell um. 1 2 3 4 5 solange b != 0 wenn a > b dann a := a - b sonst b := b - a return a Listing 1: Iterative Variante des Euklidischen Algorithmus Aufgabe 8: a) Geben Sie eine Funktion listProduct :: Num a =>[a] -> a an, die alle Elemente der Liste multipliziert und das Ergebnis zurück liefert. Verwenden Sie dazu die Funktion foldl :: (a -> b -> a) -> a -> [b] -> a. b) Komponieren Sie listProduct mit einer Funktion so, dass für eine leere Eingabe 0 das Ergebnis ist. Die Komposition kann mit dem Operator (.) :: (b -> c) -> (a -> b) -> a -> c vorgenommen werden. c) Erstellen Sie eine Funktion merge :: [[a]] -> [a], die eine Liste von Listen des gleichen Typs zu einer Liste zusammenfasst. Verwenden Sie auch hier foldl. d) Schreiben Sie eine Funktion splitBy :: (a -> Bool) -> [a] -> [[a]], die eine Liste dort trennt, wo das Prädikat wahr ist und das Element entfernt, das das Prädikat erfüllt. Verwenden Sie zur Lösung die Funktion foldr :: (a -> b -> b) -> b -> [a] -> b. Testen Sie die Funktion mit dem Test aus Listing 2. Fügen Sie den Quelltext in in eine Datei zusammen mit splitBy ein, laden Sie die Datei im GHCi mit :l Dateiname und rufen Sie check auf. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 import Test . QuickCheck import Data . List ( intercalate ) -- Strings mit Trennzeichen erzeugen splittable :: Char -> Gen String splittable x = ( listOf oneof [elements[x], arbitrary])‘suchT hat‘(any(== x)) − −obigenGeneratorzumT esten -- intercalate [ x ] . splitBy (== x ) == id prop_split_intercalate_id x s = ( intercalate [ x ] splitBy(== x)s) == scheck = quickCheck onSplittable p r o p _ s p l i t _ i n t e r c a l a t e _ i d -- splitBy in diese Datei schreiben -- und check aufrufen Listing 2: Test für splitBy Aufgabe 9: a) Geben Sie eine Funktion an, die bei einer gegebenen Preisliste den Preis für ein Produkt liefert. b) Implementieren Sie eine Funktion, die aus einer Einkaufsliste und einer Preisliste eine Liste mit Tupeln (Preis pro Stück, Menge) erstellt. c) Entwickeln Sie eine Funktion, die aus einer wie im vorherigen Schritt erzeugten Liste eine Endsumme berechnet. d) Fügen Sie alle entwickelten Funktionen in der Definition der Funktion kosten :: PreisListe -> EinkaufsListe -> Cent zusammen, sodass die Endsumme eines Einkaufs berechnet wird. –2–