Programmierung im Grossen Vorlesung 13: Ereignis

Transcription

Programmierung im Grossen Vorlesung 13: Ereignis
1
Letzte Aktualisierung: 27. Mai 2004
Programmierung im Grossen
Bertrand Meyer
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
2
Vorlesung 13:
Ereignis-Gesteuertes Design
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
Ereignis-gesteuerte Programmierung
Verbreiter
3
Bezieher
PUBLISHERS
SUBSCRIBERS
löst Ereignis aus
behandelt Ereignisse
ROUTINE
Ereignisse EVENTS
ROUTINE
ROUTINE
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
1
Vermeiden von “glue code”
4
Ereignis Erzeuger
(zB GUI)
Direkte
Anmeldung
verbindendes
Objekt
Geschäfts-Modell (Anwendungs-Logik)
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
Intern
5
ƒ Event-Aktions Tabelle
ƒ (Genauer: Event_Typ-Aktions-Tabelle)
ƒ (noch genauer: Kontext- Event_Typ-AktionsTabelle)
Event Typ
Aktion
Left_click
Save_file
…
Chair of Software Engineering
…
Programmierung im Grossen - Vorlesung 13
Ereignis-gesteuerte Programmierung
Verbreiter
6
Bezieher
PUBLISHERS
SUBSCRIBERS
löst Ereignis aus
behandelt Ereignisse
ROUTINE
Ereignisse EVENTS
ROUTINE
ROUTINE
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
2
Ereignis-Bibliothek (Event Library)
7
ƒ Klasse EVENT_TYPE
ƒ Publisher Seite, zB GUI Bibliothek:
ƒ (Einmal) deklariere Event-Typ:
click: EVENT_TYPE [TUPLE [INTEGER, INTEGER]]
ƒ (Einmal) erzeuge ein Event-Typ Objekt:
create click
ƒ Jedesmal wenn das Ereignis eintritt:
click.publish ([x_coordinate, y_coordinate])
ƒ Subscriber Seite:
click.subscribe (agent my_procedure)
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
Subscriber Varianten
8
click.subscribe (agent my_procedure)
my_button.click.subscribe (agent my_procedure)
click.subscribe (agent your_procedure (a, ?, ?, b))
click.subscribe (agent other_object.other_procedure)
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
EiffelVision style
9
my_button.click.action_list.extend (agent my_procedure)
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
3
Observer pattern (C++, Java)
update*
*
SUBSCRIBER
update+
*
attach
detach
PUBLISHER
APPCLASS
* Deferred (abstrakt)
+ Effective (implementiert)
Chair of Software Engineering
10
LIBCLASS
erbt von
Client
(verwendet)
Programmierung im Grossen - Vorlesung 13
Observer Pattern
11
In PUBLISHER:
subscribed: LIST [SUBSCRIBER]
-- Klienten subscriben bei diesem Publisher
attach (s: SUBSCRIBER) is
-- Speichern der subscription von s.
do
subscribed.extend (s)
end
publish is
do
-- Auslösen des Events.
from subscribed.start until subscribed.after loop
subscribed.item.update
subscribed.forth
end
end
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
Observer Pattern
12
In SUBSCRIBER:
subscribe (p: PUBLISHER) is
-- p’s events subscriben.
do
p.attach (Current)
end
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
4
Observer Pattern
13
In SUBSCRIBER:
subscribe (p: PUBLISHER) is
-- p’s events subscriben.
require
publisher_exists: p /= Void
do
p.attach (Current)
end
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
Observer Pattern
14
ƒ grundsätzlich:
ƒ Publisher kennen Subscriber
ƒ Subscriber können sich höchstens bei einem
Publisher anmelden
ƒ Dürfen sich höchstens für eine Aktion anmelden
ƒ Nicht wieder verwendbar — muss für jede
Anwendung neu programmiert werden
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
Event Library
15
ƒ Publisher, z.B. GUI Library:
ƒ Deklaration und Creation:
click: EVENT_TYPE [TUPLE [INTEGER, INTEGER]]
ƒ Auslösen des Events mit Argumenten.
click.publish ([x, y])
ƒ Subscriber:
my_button.click.subscribe (agent r)
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
5
Observer pattern (C++, Java)
update*
*
SUBSCRIBER
update+
*
attach
detach
APPCLASS
* Deferred (abstrakt)
+ Effective (implementiert)
Chair of Software Engineering
PUBLISHER
LIBCLASS
erbt von
Client
(verwendet)
Programmierung im Grossen - Vorlesung 13
Hintergrundinformation: .NET
ƒ
ƒ
ƒ
ƒ
ƒ
ƒ
ƒ
ƒ
ƒ
ƒ
16
17
Basis für zukünftige Windows Entwicklung
Seit 2000
Schicht über dem Betriebsystem
Unterstützt fortgeschrittene Web Technologien, speyiell
durch ASP.NET
Basiert auf einem Object Modell
Microsoft Sprachen: C#, Visual Basic .NET
Andere unterstützte Sprachen: Eiffel, Cobol, Oberon
Zahlreiche Bibliotheken und wieder verwendbare
Komponenten
Internationaler Standard (Common Language Interface)
durch ECMA und ISO
Nicht-Windows Implementation: Mono
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
.NET Event-Delegate Mechanismus
18
ƒ Publisher oder Subscriber:
D1 ƒ Führe einen Nachfahren ClickArgs von EventArgs ein, der
die Typen der Argumente von myProcedure wiederholt.
(Fügt eine Klasse hinzu.)
public class ClickArgs
{
int x, y;...
}
D2 ƒ Deklariere einen Delegate-Typ ClickDelegate basierend
auf dieser Klasse. (Fügt einen Typ hinzu.)
public void delegate ClickDelegate
(Object sender, ClickArgs e);
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
6
.NET Delegates: Publisher
19
D3 ƒ Deklariere einen neuen Event-Typ Click basierend auf dem Typ
ClickDelegate. (Fügt einen Typ hinzu.)
public event ClickDelegate Click;
D4 ƒ Schreibe Prozedur OnClick für die Behandlung. (+ 1 Routine.)
protected void OnClick (ClickArgs e)
{
if (Click != null)
Click (this, e);
}
D5 ƒ Für jedes Auftreten des Events erzeuge eine Instanz von
ClickArgs und übergebe arg Werte an den Konstruktor. (Fügt ein
Laufzeit-Objekt hinzu.)
ClickArgs myClickArgs = new ClickArgs (h, v);
D6 ƒ Für jedes Auftreten, feure den Event
OnClick (myClickArgs);
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
.NET Delegates: Subscriber
20
ƒ Um eine Routine myProcedure anzumelden:
D7 ƒ Deklariere einen Delegate myDelegate vom Typ
ClickDelegate. (Kann mit dem folgenden Schritt
kombiniert werden.)
D8 ƒ Instanziiere es mit myProcedure als
Konstruktor-Argument.
ClickDelegate myDelegate =
new ClickDelegate (myProcedure)
D9 ƒ Füge es der Delegate-Liste für den Event hinzu.
yourButton.Click += myDelegate
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
.NET Delegates
21
ƒ event ist ein Schlüsselwort der Sprache
(besonderes Feature einer Klasse). Event-Typen
sollten aber wie normale Objekte behandelt
werden.
ƒ Kann keine geschlossene Argumente haben: für
etwas Equivalentes zu
r (a, ?, ?, b)
muss man eine Wrapper-Routine schreiben, die
vom Delegate verwendet wird.
ƒ Kann kein offenes Ziel haben: für etwas wie
{TYPE}.r (...)
muss man eine Wrapper-Routine schreiben.
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
7
Event library
22
ƒ Publisher, e.g. GUI library:
ƒ Declare and create:
click: EVENT_TYPE [TUPLE [INTEGER, INTEGER]]
ƒ Trigger each event with arguments.
click.publish ([x, y])
ƒ Subscriber (to subscribe a routine r):
my_button.click.subscribe (agent r)
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
Gelerntes
23
ƒ Vermeide Magie: Was für den Sprach-Designer
verfügbar ist, sollte für den Programmierer
verfügbar sein
ƒ Rolle der Sprach-Mechanismen: Generizität,
beschränkte Generizität, Tupel
ƒ Wichtig, die richtige Abstraktion zu wählen
ƒ Observer Pattern: PUBLISHER, SUBSCRIBER
ƒ .NET: Event, Delegate, Event-Typ, DelegateTyp?
ƒ Eiffel Event Bibliothek: EVENT_TYPE
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
Vermeiden von “glue code”
24
Ereignis Erzeuger
(zB GUI)
Direkte
Anmeldung
verbindendes
Objekt
Geschäfts-Modell (Anwendungs-Logik)
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
8
Zusätzliches Material
25
ƒ Eiffel: The Language, 3rd Auflage (Entwurf), Kapitel 25
→ Erhältlich
http://www.inf.ethz.ch/~meyer/ongoing/etl/agent.pdf
(Login: Talkitover; Passwort: etl3)
ƒ Paper über Event-basierte Programmierung
→ Erhältlich
http://www.inf.ethz.ch/~meyer/ongoing/events.pdf
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
26
Ende Vorlesung 13
Chair of Software Engineering
Programmierung im Grossen - Vorlesung 13
9