# Rückmeldung bei Empfang



## DarkGuardian (30. Aug 2008)

Hallo zusammen

Leider ist es bei mir schon etwas her, dass ich viel mit Java gemacht habe. Aber momentan arbeite ich an einem Servlet, u.a. um mein Wissen wieder aufzufrischen.

Dabei habe ich in meiner Software einen Thread, der Nachrichten abschickt und empfängt. Die empfangenen Nachrichten werden auch schon passend an den Hauptthread weitergeben, indem ich diese dort in einem Vector hinterlege. Zudem setze ich dort eine Variable, die den aktuellen Verbindungszustand darstellt. 

Nun möchte ich den Hauptthread benachrichtigen, dass sich der Zustand geändert oder eine Nachricht empfangen wurde. Leider weiß ich nicht, wie ich das am besten machen kann. In C++ würde ich das z.B. über eine Windowsnachricht machen. Aber ich weiß, dass es in Java Events gibt, auf die theoretisch der Hauptthread als Listener reagieren könnte. Aber irgendwie finde ich diesen Mechanismus nur im GUI-Bereich.

Wie kann ich die Benachrichtigung am besten realisieren? Und könnt ihr mir evtl. ein grobes Codebeispiel dazu geben?


----------



## Murray (30. Aug 2008)

Sieh Dir mal die Methoden wait und notify in java.lang.Object an.


----------



## DarkGuardian (31. Aug 2008)

Danke für den Hinweis, aber ich glaube nicht, dass mir notify und wait da weiterhelfen. Denn ich kann ja schlecht den Hauptthread per wait so lange pausieren lassen, bis der Kommunikationsthread per notify eine neue Nachricht meldet. Die Applikation soll ja trotzdem normal ihre Aufgaben erledigen.

Ansich könnte ich einen Timer laufen lassen, der alle x ms nachsieht, ob Nachrichten eingetroffen sind. Aber diese Art von polling ist nicht das was ich suche. Ich will dem Hauptthread nur signalisieren, dass eine Nachricht eingetroffen ist. Die Applikation kann aber dazwischen nicht stehen bleiben.


----------



## DarkGuardian (1. Sep 2008)

Gibt es keine weiteren Idee oder Vorschläge zu dem Thema? Ist es so offensichtlich, wie man das Problem löst, dass ich einfach nicht darauf komme, da ich schon zu kompliziert ansetze (oder habe ich wait/notify nicht korrekt verstanden?)?

Es dürfte in meinen Augen kein seltenes Problem sein, denn ein Empfangsthread, der Nachrichten über eine Schnittstelle asynchron empfängt und bereitstellt, dürfte doch recht häufig sein. Daher vermute ich auch, dass es für mein Problem eine einfache Lösung gibt. Ich hoffe nur, dass mir zu dieser einen passenden Tipp geben kann.


----------



## DarkGuardian (1. Sep 2008)

Korrektu
 Im letzten Satz fehlt ein jemand:
Ich hoffe nur, dass mir zu dieser *jemand* einen passenden Tipp geben kann.


----------



## tuxedo (2. Sep 2008)

>> Nun möchte ich den Hauptthread benachrichtigen, dass sich der Zustand geändert oder eine Nachricht empfangen wurde. Leider weiß ich nicht, wie ich das am besten machen kann.

Wieso machst du nicht einen Listener?

Der Hauptthread registriert sich beim Sende/Empfangsthread. Wird etwas empfangen, meldet der Thread dies beim Hauptthread über die entsprechende Listener-Methode.

- Alex


----------



## DarkGuardian (2. Sep 2008)

Allgemein müsste ein Listener diese Aufgabe erledigen können. Ich bin mir nur nich sicher, wie ich diesen umsetzen kann. Wo ist denn der genaue Unterschied zwischen einem Observerpattern und einem Listener?

Ansich melden sich bei beiden Objekte an, die eine Benachrichtigung für etwas wollen. Sobald ein entsprechendes Ereigniss auftritt (z.B. Empfang einer Nachricht), werden bei beiden Lösungen die Liste der angemeldeten Objekte durchgegangen und benachrichtigt. Nur bei einem Listener wird dabei ein Event-Objekt genutzt. Worin besteht da der Unterschied?

Wenn mein Thread den Listener über eine Synchronized-Methode bescheid gibt, bleibt der Thread doch mit der Verarbeitung an der Stelle so lange stehen, bis die Methode abgearbeitet wurde, oder? Da es sich bei mir um eine Netzwerkkomponente handelt, kann ich nicht sagen, wie lange die Abarbeitung dieser dauert. Ich kann aber ja nicht in der Verarbeitungszeit die Netzwerkkommunikation stehen lassen.

Verstehe ich nun die Funktionsweise diese Varianten falsch oder bieten mir diese wirklich nicht das was ich suche? Ich hoffe, hiermit ist deutlich geworden, worin ich momentan mein Problem sehe.


----------



## tuxedo (2. Sep 2008)

DarkGuardian hat gesagt.:
			
		

> Allgemein müsste ein Listener diese Aufgabe erledigen können. Ich bin mir nur nich sicher, wie ich diesen umsetzen kann. Wo ist denn der genaue Unterschied zwischen einem Observerpattern und einem Listener?
> 
> Ansich melden sich bei beiden Objekte an, die eine Benachrichtigung für etwas wollen. Sobald ein entsprechendes Ereigniss auftritt (z.B. Empfang einer Nachricht), werden bei beiden Lösungen die Liste der angemeldeten Objekte durchgegangen und benachrichtigt. Nur bei einem Listener wird dabei ein Event-Objekt genutzt. Worin besteht da der Unterschied?



Es verpflichtet dich keiner ein Event-Objekt zu benutzten. Das kannst du handhaben wie du willst.



> Wenn mein Thread den Listener über eine Synchronized-Methode bescheid gibt, bleibt der Thread doch mit der Verarbeitung an der Stelle so lange stehen, bis die Methode abgearbeitet wurde, oder? Da es sich bei mir um eine Netzwerkkomponente handelt, kann ich nicht sagen, wie lange die Abarbeitung dieser dauert. Ich kann aber ja nicht in der Verarbeitungszeit die Netzwerkkommunikation stehen lassen.


Na dann ist es an dir, die Listener-Methode so zu gestalten dass sie nict allzulange blockiert. Aber das ist eher ein generelles Architekturproblem.



> Verstehe ich nun die Funktionsweise diese Varianten falsch oder bieten mir diese wirklich nicht das was ich suche? Ich hoffe, hiermit ist deutlich geworden, worin ich momentan mein Problem sehe.



Nein, und nein, du hast das schon richtig verstanden.

Gruß
Alex


----------



## DarkGuardian (2. Sep 2008)

Danke für deine schnelle Rückmeldung



			
				alex0801 hat gesagt.:
			
		

> DarkGuardian hat gesagt.:
> 
> 
> 
> ...



Somit sind also Listener nur eine Umsetzung des Observerpatterns.



			
				alex0801 hat gesagt.:
			
		

> > Wenn mein Thread den Listener über eine Synchronized-Methode bescheid gibt, bleibt der Thread doch mit der Verarbeitung an der Stelle so lange stehen, bis die Methode abgearbeitet wurde, oder? Da es sich bei mir um eine Netzwerkkomponente handelt, kann ich nicht sagen, wie lange die Abarbeitung dieser dauert. Ich kann aber ja nicht in der Verarbeitungszeit die Netzwerkkommunikation stehen lassen.
> 
> 
> Na dann ist es an dir, die Listener-Methode so zu gestalten dass sie nict allzulange blockiert. Aber das ist eher ein generelles Architekturproblem.


OK, aber da die verarbeitende Methode nicht Teil meiner Netzwerkkomponente ist, kann ich eine Kommunikation ohne Blockierungen nicht garantieren. Ich muss also einen Hinweis geben, dass die verarbeitende Methode "kurz" sein muss. Oder gibt es da eine andere Möglichkeit in Java?

Gruß DarkGuardian


----------



## tuxedo (2. Sep 2008)

Wie du das entkoppelst bleibt dir überlassen. Wenn die einzelnen Listener-Aufrufe dein Netzwerk blockieren würden (oder umgekehrt), würde ich hier nochmal einen Thread einsetzen der die "Events" entkoppelt abfeuert.

- Alex


----------



## DarkGuardian (2. Sep 2008)

Irgendwie finde ich da keine Lösung die mich wirklich überzeugt. Nun habe ich das über einen Timer realsisiert, der alle x ms das Verteilen der empfangenen Nachrichten übernimmt. Zwar bin ich kein Fan von diesem Polling, aber irgendwie klingt das für mich zu umständlich, dafür einen extra Thread aufzusetzen, der auf das Event wartet und dann die Verteilung anstößt.

Mit C++ unter Windows hätte ich das über Windowsnachrichten und PostMessage gemacht. Aber eine vergleichbare Lösung finde ich momentan nicht für Java.

Trotzdem natürlich vielen Dank an dich (alex0801). Das hat mir auf jeden Fall weiter geholfen.


----------



## FArt (2. Sep 2008)

Ich denke mit einem Observer würde man erreichen was du möchstest. Wenn du unbedingt asynchron entoppeln möchtest (musst) kann man das über Observer und Dispatcher-Thread selber lösen, oder man bedient sich fertiger APIs, wie z.B. JMS.


----------



## DarkGuardian (2. Sep 2008)

Das Verteilen läuft sowieso über ein Observerpattern. Das war für mich von Anfang an klar. Nur die asynchrone Entkopplung macht mir noch etwas sorgen. Dieses JMS kenne ich noch nicht, aber ich werde mir es mal ansehen. Ansonsten werde ich erst einmal mit meiner Polling-Lösung leben. Falls es doch noch zu Problemen kommt, weiß ich ja, wo ich ansetzen muss.


----------



## FArt (2. Sep 2008)

Obige Bemerkung war noch mal als Denkanstoß gedacht. JMS ist dafür sicher oversized... aber eine Queue wäre doch was...


----------



## DarkGuardian (2. Sep 2008)

Ich glaube auch, dass JMS viel mehr bietet als ich wirklich brauche. Bei ersten Tests scheint das auch so zu klappen (mit Timern). Das muss ich halt später mit mehr Last testen, um zu sehen, ob es wirklich klappt.

Ja, so eine Nachrichtenqueue wäre echt etwas Feines. Aber ok, die habe ich momentan nicht und kann sie mir anscheinend auch nicht ohne großen Aufwand besorgen. Daher stelle ich das als "nice to have" erst mal zurück.

Vielen Dank für die Hilfe.


----------

