Funktionales Programmieren Einführung Berthold Hoffmann Studiengang Informatik Universität Bremen Wintersemester 2009/2010 (Vorlesung am 28. Oktober 2009) Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 1 / 146 Gestatten? Berthold Hoffmann Koordinaten Interessen • Mitarbeiter in der • • • • AG Krieg-Brückner Email: hof@informatik. . . Büro: Cartesium 2.48 Enrique-Schmidt-Str. 5 Telefon: 218-64 222 Sprechstunde: Mo 10-12 (und nach Vereinbarung) Berthold Hoffmann (Universität Bremen) • Übersetzer • Programmiersprachen • visuelle Sprachen • Graphtransformation Funktionales Programmieren Winter 09/10 2 / 146 Einführung (28. Oktober 2009) 1 Einführung Vergleich von Programmierstilen Daten sind Wertemengen Mustervergleich und Rekursion Polymorphe Typen und Funktionen Funktionen sind Werte Eigenschaften von Funktionen 2 Organisation Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 3 / 146 Eine Frage von Stil Praktische Informatik 1 und 2 • Imperativ : Befehle verändern Zustände im Speicher • Objektorientiert: Objekte tauschen Nachrichten aus • Zustandsbasiertes Programmieren Praktische Informatik 3 • deklaratives, regelbasiertes Programmieren Was soll getan werden? – nicht wie wird es getan? • Funktional: Funktionen werten Ausdrücke aus • Logisch: Prädikate beweisen Anfragen Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 4 / 146 Die wichtigsten Programmierstile Programmieren regelbasiert zustandsbasiert imperativ HH H funktional HH H logisch objektorientiert Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 5 / 146 Ein objektorientiertes Programm Beispiel (Listenverkettung Objektorientiert) class List { int entry; List next; public void cat(List ys){ List last = next; while (last != null) last = last.next; last = ys; } ... } Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 6 / 146 Beobachtungen zum objektorientiertem Stil Nachricht: ℓ1 .cat(ℓ2 );ℓ1 .cat(ℓ2 ) ℓ1 :List ℓ1 :List 1 List 1 List ℓ2 :List 2ℓ2 :List 2 null 3 null 3 null ℓ1 :List 1 List 2ℓ2 :List 3 • Daten sind beliebige Geflechte (Graphen) von Objekten • Objekte haben Zustände, Methoden haben Seiteneffekte Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 7 / 146 Funktionales Programmieren in der Nussschale Programmieren ohne Zustände und Seiteneffekte • Daten sind Wertemengen • Algorithmen sind (mathematische) Funktionen • Funktionen sind Werte (Argument, Ergebnis einer Funktion) Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 8 / 146 Werte sind Ausdrücke über Konstruktoren • parameterlos: Z, Empty, . . . • einstellig: S, . . . • zweistellig: Cons, . . . • ... • Ausdrücke: S (S Z) Cons (S (S Z)) (Cons (S Z) Empty) • einfache Argumente werden nicht geklammert! Empty S Cons S S Cons Z Z Z Empty Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 9 / 146 Datentypen und Funktionsgleichungen Beispiel (Natürliche Zahlen) data Nat =Z | S Nat plus :: Nat → Nat → Nat plus Z y=y plus (S x) y = S (plus x y) Werte sind getypt: Z :: Nat S :: Nat → Nat S (S Z) :: Nat Berthold Hoffmann (Universität Bremen) • Gleichungen für verschiedene Fälle • Mustervergleich • strukturelle Rekursion Funktionales Programmieren Winter 09/10 10 / 146 Typen und Funktionen können polymorph sein Beispiel (Listen) data List t = Empty | Cons t (List t) cat :: List t → List t → List t cat Empty ys = ys cat (Cons x xs) ys = Cons x (cat xs ys) Listen sind homogen • Empty ::List t • Cons Empty Empty ::List (List t) • Cons Empty (Cons Z Empty) ::⊥ illegal Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 11 / 146 Funktionen auswerten = Gleichungen anwenden cat (Cons (S (S Z)) (cat (Cons (S Z) Empty) (Cons Z Empty)) cat (Cons (S (S Z)) (Cons (S Z) (cat Empty (Cons Z Empty))) cat (Cons (S (S Z)) (Cons (S Z) (Cons Z Empty)) cat (Cons (S (S Z)) (Cons (S Z) Empty)) (Cons Z Empty) Cons (cat (S (S Z)) (Cons (S Z) Empty) (Cons Z Empty)) Cons (S (S Z)) (Cons (S Z) (cat (Empty) (Cons Z Empty))) Cons (S (S Z)) (Cons (S Z) (Cons Z Empty)) • Argumente bleiben unverändert • Ergebnis hängt allein von den Argumenten ab: referentielle Transparenz Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 12 / 146 Auswertungsreihenfolge cat Cons cat Cons S Cons S Empty Cons Cons + S S Cons S S Empty Z Empty Z Z Z Empty Z Z • immer links außen: outermost, by-need, lazy • immer links innen: inermost, by-value, strikt • Ergebnisse sind gleich (Konfluenz) • lazy Auswertung vermeidet Fehler (ist normalisierend) Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 13 / 146 Komplexität der Auswertung • Zeitaufwand ∼ Anzahl der Gleichungsanwendungen • Platzbedarf ∼ Anzahl der Konstruktoraufrufe (plus Platz für Zwischenergebnisse auf dem Stack) • plus, cat: linear im ersten Argument (Zeit und Platz) Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 14 / 146 Funktionen sind Werte • a → b ist der Typ der Funktionen von Typ a nach Typ b • \x → E konstruiert eine namenlose Funktion (λx.E ) • Funktionen als Argument oder Ergebnis Beispiel (Map und Komposition) map :: (a → b) → List a → List b map f Empty = Empty map f (Cons x xs) = Cons (f x) (map f xs) comp :: (b → c) → (a → b) → (a → c) comp f g x = f (g x) Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 15 / 146 Kombination von Funktionen höherer Ordnung doublelist :: List Nat → List Nat doublelist = map (\x → plus x x) twice :: (a → a) → a → a twice f = comp f f Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 16 / 146 Formale Eigenschaften von Funktionen • Jede Gleichung definiert ein Lemma • damit können weiterer Lemmata bewiesen werden • für den Nachweis von Termination und Korrektheit Beispiel (Gleichungen der Verkettung) ∀ℓ ∈ List τ : cat Empty ℓ = ℓ ′ ∀x ∈ τ, ℓ, ℓ ∈ List τ : cat (Cons x ℓ) ℓ′ = Cons x (cat ℓ ℓ′ ) Lemma (Assoziativität und Neutrales Element) ∀ℓ ∈ List τ : cat Empty ℓ = ℓ = cat ℓ Empty ∀ℓ, ℓ′ , ℓ′′ ∈ List τ : cat (cat ℓ ℓ′ ) ℓ′′ = cat ℓ (cat ℓ′ ℓ′′ ) Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 17 / 146 Theorem: ∀ℓ ∈ List τ : cat ℓ Empty = ℓ (1) Beweis (Induktion über die Struktur) Induktionsanfang. Wenn ℓ = Empty in (1), gilt: cat Empty Empty = Empty 1. Gleichung von cat Induktionsannahme. Gelte (1) für irgend ein ℓ ∈ List τ . Induktionsschritt. Dann gilt (1) auch für Cons x ℓ, für irgend ein x: cat (Cons x ℓ) Empty = Cons x (cat ℓ Empty) = Cons x (cat Empty ℓ) = Cons x ℓ Berthold Hoffmann (Universität Bremen) 2. Gleichung von cat nach Induktionsannahme 1. Gleichung von cat Funktionales Programmieren Winter 09/10 18 / 146 Der Kern von Haskell Datentypen Funktionen data List t = Empty | Cons t (List t) cat :: List t → List t → List t cat Empty ys = ys cat (Cons x xs) ys = Cons x (cat xs ys) Funktionen höherer Ordnung map :: (a → b) → List b map f Empty map f (Cons x xs) Cons (f x) (map f Berthold Hoffmann (Universität Bremen) Funktionales Programmieren List a → = Empty = xs) Winter 09/10 19 / 146 Wozu der Spaß? You can never understand one language until you understand at least two. Ronald Searle, engl. Karrikaturist (1920– ) • InformatikerInnen sollten alle Programmierstile kennen • abstrakter Entwurf von Datenstrukturen und Algorithmen • Eigenschaften von Programmen leichter nachweisen • innovative Konzepte kennen lernen Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 20 / 146 Meine Lehrziele – Ihre Lernziele? • Programmieren mit FUN ◮ abstrakt, kurz und knapp ◮ systematisch und übersichtlich (YSWIM?) ◮ unwichtig: Effizienz • Argumentieren ◮ Eigenschaften finden ◮ Eigenschaften nachweisen ◮ Aufwand abschätzen Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 21 / 146 Nachlese(n) P. J. Landin. The next 700 programming languages. Comm. ACM, 9(3):157–166, 1966. eamericonarticle J. Backus. Can Programming be Liberated from the van-Neumann Style? Comm. ACM, 21(8):613–641, 1978. eamericonarticle Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 22 / 146 Zusammenfassung – Ausblick Heute • Daten sind Wertemengen, mit Konstruktoren aufgebaut • Typen sind rekursiv und polymorph • Funktionen sind rein • Funktionen werden mit Gleichungen definiert mit Mustervergleich und Rekursion • Funktionen sind auch nur Werte (Argumente, Ergebnisse) • Eigenschaften können durch Induktion gezeigt werden Nächstes Mal • Funktionen auf Zahlen, Listen, Tupeln • Umsetzung in Haskell Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 23 / 146 Einführung (28. Oktober 2009) 1 Einführung 2 Organisation Tutorien, Aufgaben, Scheine, . . . Inhalt des Kurses Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 24 / 146 Material zur Veranstaltung www.informatik.uni-bremen.de/agbkb/lehre/pi3/ • Skript (mit lauffähigen Haskell-Programmen) • Folienkopien • Ausgabe der Aufgaben • Haskell: Beschreibung, Bibliothek, Tutorials • Hinweise auf Lehrbücher und Links stud.ip (elearning.uni-bremen.de) • Einteilung in Tutorien • Anmeldungen zum Fachgespräch Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 25 / 146 Tutorien – Programmieren in Haskell • Gruppen • • • • 1 MO 10–12 MZH 1380 Christian Maeder maeder 2 DI 08–10 IW3 0330 Jasper van de Ven jasper 3 DI 10–12 MZH 7220 Julia Seiter jseiter 4 Di 10–12 MZH 7250 Berthold Hoffmann hof 5 DI 12–14 MZH 7210 Jasper van de Ven jasper 6 MI 08–10 MZH 7250 Dominik Dietrich dodi Anmeldung über stud.ip Lastenausgleich im ersten Tutorium Beginn: nächste Woche Montag bzw. Dienstag Inhalt: Vertiefung, Vor- und Nachbereitung der Aufgaben Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 26 / 146 Aufgaben – selber in Haskell programmieren • wöchentliche Ausgabe der Übungsblätter auf der Webseite • • • • • • Donnerstag abends Abgabe zwei Wochen später per Email an Tutoren Besprechung in den Tutorien Reine Bearbeitungszeit 1 Woche Voraussichtlich 11 Übungsblätter Maximal 10 Punkte pro Blatt Bewertung in der Regel: 40% Code, 40% Dokumentation 20% Tests. Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 27 / 146 Scheinkriterien – Vorschlag • Alle Übungsblätter müssen bearbeitet werden • Ein Übungsblatt ist bearbeitet: > 20% • Für einen Schein braucht man 50% der Punkte. • Individualität der Leistung wird festgestellt durch ein Fachgespräch (Mitte Februar) Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 28 / 146 Spielregeln für die Übungsaufgaben • Bearbeitung der Aufgaben in Dreiergruppen • Jeder muss die abgegebenen Lösungen erklären können! • Quellen müssen angegeben werden ◮ gruppenübergreifende Zusammenarbeit ◮ Internet-Recherche, Literatur usw. • Erster Täuschungsversuch: 0 Punkte (Blatt zählt trotzdem als “bearbeitet”) • Zweiter Täuschungsversuch: kein Schein • Terminprobleme rechtzeitig mit Tutoren absprechen (sonst: 0 Punkte!) Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 29 / 146 Lernaufwand • 6 ECTS-Punkte ≈ 8h Arbeit pro Woche ◮ 90 min Vorlesung ◮ 90 min Tutorium ◮ 3h für Übungsaufgaben ◮ 2h Vor- und Nachbereitung • Wer deutlich mehr arbeiten muss, darf hier meckern! • Wer in anderen LVs deutlich mehr arbeiten muss, soll dort meckern! Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 30 / 146 Inhalt • Prinzipien des funktionalen Programmierens • Praktische Umsetzung mit Haskell ◮ einfache Werte, Listen ◮ pattern matching, Rekursion, Polymorphie ◮ algebraische Datentypen, ◮ Module ◮ abstrakte Datentypen, ◮ Typklassen, Module ◮ Funktionen höherer Ordnung ◮ Korrektheit und Aufwand ◮ Monaden, Zustände, I/O • Form: Präsention, Tafel, Demo • Interaktion ausdrücklich erwünscht! Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 31 / 146 Lehrbücher zum Thema I Manuel M. T. Chakravarty and Gabriele C. Keller. Einführung in die Programmierung mit Haskell. Pearson Studium, München, 2004. beamericonbook Gert Smolka. Programmierung – eine Einführung in die Informatik mit Standard ML. Oldenbourg Wissenschaftsverlag, München, 2008. beamericonbook Peter Pepper. Funktionale Programmierung in OPAL, ML, HASKELL und GOFER. Springer, Berlin;Heidelberg;New York, 2 Auflage, 2003. beamericonbook Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 32 / 146 Lehrbücher zum Thema II Simon Thompson. The Craft of Functional Programming. International Computer Science Series. Addison Wesley, Reading, Massachusetts, 2. edition, 1999. beamericonbook Paul Hudak. The Haskell School of Expression: Learning Functional Programming through Multimedia. Cambridge University Press, Cambridge, 2000. beamericonbook Graham Hutton. Programming in Haskell. Cambridge University Press, Cambridge;New York;Melbourne;Madrid, 2007. beamericonbook Berthold Hoffmann (Universität Bremen) Funktionales Programmieren Winter 09/10 33 / 146