Reaktive Programmierung
Vorlesung 3 vom 21.04.15: Funktional-Reaktive Programmierung
Christoph Lüth & Martin Ring Universität Bremen Sommersemester 2015
17:10:26 2015-05-19 1 [12]
Fahrplan
I Teil I: Grundlegende Konzepte
IWas ist Reaktive Programmierung?
INebenläufigkeit und Monaden in Haskell
IFunktional-Reaktive Programmierung
IEinführung in Scala
IDie Scala Collections
IScalaTest und ScalaCheck I Teil II: Nebenläufigkeit
I Teil III: Fortgeschrittene Konzepte
2 [12]
Das Tagemenü
I Funktional-Reaktive Programmierung(FRP) istreinfunktionale, reaktive Programmierung.
I SehrabstraktesKonzept — im Gegensatz zu Observables und Aktoren.
I Literatur: Paul Hudak,The Haskell School of Expression, Cambridge University Press 2000, Kapitel 13, 15, 17.
I Andere (effizientere) Implementierung existieren.
3 [12]
FRP in a Nutshell
I Zwei Basiskonzepte
I Kontinuierliches, über der Zeit veränderlichesVerhalten:
typeTime = Float
typeBehaviour a = Time→ a
I Diskrete Ereignissezu einem bestimmten Zeitpunkt:
typeEvent a = [ (Time, a ) ]
I Obige Typdefinitionen sindSpezifikation, nichtImplementation
4 [12]
Verhalten: erste einfache Beispiele
I Ein kreisender und ein pulsierender Ball:
ci rc , pulse :: Behavior Region
c i r c = t r a n s l a t e ( cos time , s i n time) ( e l l 0.2 0.2) pulse = e l l ( cos time∗ 0.5) ( cos time∗ 0.5)
I Was passiert hier?
I Basisverhalten:time :: Behaviour Time,constB :: a→Behavior a
I Grafikbücherei: DatentypRegion, Funktion Ellipse
I Liftings (∗,0.5,sin, . . . )
5 [12]
Reaktive Animationen: Verhaltensänderung
I Beispiel: auf Knopfdruck Farbe ändern:
color1 :: Behavior Color
color1 = red ‘ untilB ‘ lbp− blue color2r = red ‘ untilB ‘ ce where
ce = ( lbp− blue ‘ untilB ‘ ce ) .|. (key− yellow ‘ untilB ‘ ce ) I Was passiert hier?
I untilBkombiniert Verhalten:
untilB :: Behavior a →Event ( Behavior a) →Behavior a
I=istmapfür Ereignisse:
(=) :: Event a →(a→b) →Event b (− ) :: Event a→b→Event b e− v = e =λ_→v
IKombination von Ereignissen:
6 [12]
Der Springende Ball
ball2 = paint red ( t r a n s l a t e (x , y) ( e l l 0.2 0.2)) whereg = −4
x = −3 + i n t e g r a l 0.5 y = 1.5 + i n t e g r a l v v = i n t e g r a l g ‘ switch ‘
( h i t ‘ snapshot_ ‘ v = λv ’→
l i f t 0 (−v ’ ) + i n t e g r a l g) h i t = when (y<∗ −1.5)
I Nützliche Funktionen:
i n t e g r a l :: Behavior Float → Behavior Float snapshot :: Event a→ Behavior b→ Event (a , b) I Erweiterung: Ball ändert Richtung, wenn er gegen die Wand prallt.
7 [12]
Implementation
I Verhalten, erste Annäherung:
dataBeh1 a = Beh1 ( [ ( UserAction , Time) ]→Time→ a) I Problem:SpeicherleckundIneffizienz
I Analogie: suche insortiertenListen i n L i s t :: [ Int ] → Int →Bool i n L i s t xs y = elem y xs
manyInList ’ :: [ Int ]→ [ Int ]→ [ Bool ] manyInList ’ xs ys = map ( i n L i s t xs ) ys I Besser Sortiertheit direkt nutzen
manyInList :: [ Int ] → [ Int ] → [ Bool ]
8 [12]
Implementation
I Verhalten werdeninkrementell abgetastet:
dataBeh2 a
= Beh2 ( [ ( UserAction ,Time) ] → [Time] → [ a ] ) I Verbesserungen:
I Zeit doppelt, nureinmal
I Abtastung auchohne Benutzeraktion
I Currying data Behavior a
= Behavior ( ( [Maybe UserAction ] , [ Time] ) → [ a ] ) I Ereignisse sind im Prinzipoptionales Verhalten:
data Event a = Event ( Behaviour (Maybe a))
9 [12]
Längeres Beispiel: Paddleball
I Das Paddel:
paddle = paint red ( t r a n s l a t e ( f s t mouse, −1.7) ( rec 0.5 0.05)) I Der Ball:
pball v e l =
let xvel = v e l ‘stepAccum ‘ xbounce− negate xpos = i n t e g r a l xvel
xbounce = when (xpos>∗ 2 | | ∗xpos<∗ −2) yvel = v e l ‘stepAccum ‘ ybounce− negate ypos = i n t e g r a l yvel
ybounce = when (ypos>∗1.5
| | ∗ypos ‘between ‘ (−2.0,−1.5) &&∗
f s t mouse ‘between ‘ (xpos−0.25,xpos+0.25)) in paint yellow ( t r a n s l a t e (xpos , ypos) ( e l l 0.2 0.2)) I Die Mauern:
walls :: Behavior Picture I . . . und alles zusammen:
paddleball v e l = walls ‘ over ‘ paddle ‘ over ‘ pball v e l
10 [12]
Warum nicht in Scala?
I Lifting und Typklassen fürsyntaktischen Zucker
I Aber: zentrales Konzept sindunendlicheListen (Ströme) mit nicht-strikteAuswertung
I Implementation mit Scala-Listen nicht möglich
I Benötigt:Strömeals unendliche Listen mit effizienter, nicht-strikter Auswertung
I Möglich, aber nicht für diese Vorlesung I Generelle Schwäche:
I Fundamentalnicht-kompositional— ist gibteineHauptfunktion
I Fehlerbehandlung, Nebenläufigkeit?
11 [12]
Zusammenfassung
I Funktional-Reaktive Programmierung am Beispiel FAL (Functional Animation Library)
I Zwei Kernkonzepte: kontinuierlichesVerhaltenund diskreteEreignisse
I Implementiert in Haskell, Systemverhalten als unendlicher Strom von Zuständen
I ErlaubtabstrakteProgammierung vonreaktiven Animationen I Problem ist mangelndeKompositionalität
I Nächste Vorlesungen:Scala!
12 [12]