Newsgroup Archiv - Beiträge

auf www.Bastie.de

# Thread für Server

Frager: Jens Tinz vom: Mittwoch, 29. November 2000
Hallo!
Ich arbeite gerade an einem kleinen Server, der Daten zwischen Applets weiterleitet. Momentan wird fuer jede Verbindung ein neuer Thread gestartet, der auf dem Socket lauscht.
Es ist jedoch recht wahrscheinlich, dass mehrere hundert Verbindungen gleichzeitig geoeffnet sein werden. Vermutlich tauchen dann Probleme mit der grossen Anzahl von Threads auf.
Wie implementiere ich einen Server, der weniger Threads verwendet? Gibt es irgendwo Beispiele, die ich mir ansehen kann?
Vielen Dank, Jens
1. Antwort: Ingo R. Homann vom: Mittwoch, 29. November 2000
Hi!
Nun, also wenn Du n Verbindungen brauchst, dann kommst Du IMHO auch nicht um n Threads herum (Es sei denn, dein Protokoll ist so angelegt, dass es z.B. ausreicht, in einem bestimmten Zeittakt zu senden/empfangen...)
Einen Server zu implementieren, der nur eine maximale Anzahl von Verbindungen zulaesst, sollte nicht schwierig sein. Aber das ist vermuitlich nicht das, was Du willst...
Wenn es dir um des *Starten* der Threads geht, das dir zu lange dauert, verwende einen Thread-Pool.
Aber ich denke, die praktikabelste Loesung duerfte die erste (mit dem
entsprechenden Protokoll) sein.
Ciao, Ingo
2.1 Antwort: Thomas Foerster vom: Mittwoch, 29. November 2000
> "Nun, also wenn Du n Verbindungen brauchst, dann kommst Du IMHO auch nicht um n Threads herum (Es sei denn, dein Protokoll ist so angelegt, dass es z.B. ausreicht, in einem bestimmten Zeittakt zu senden/empfangen...)"
Dann müssten die einzelnen Clients auch untereinander synchronisiert sein, und das halte ich eher für unwahrscheinlich.
> "Einen Server zu implementieren, der nur eine maximale Anzahl von Verbindungen zulaesst, sollte nicht schwierig sein. Aber das ist vermuitlich nicht das, was Du willst..."
Wenn die Hardware bzw. das BS nicht so viele Threads mit angemessener Performance zulassen, wird einem nichts anderes übrig bleiben. Bei HTTP- oder FTP-Servern ist das ja auch nicht anders.
> "Wenn es dir um des *Starten* der Threads geht, das dir zu lange dauert, verwende einen Thread-Pool."
Sehr wichtiger Punkt! Gut, dass Du es erwähnst. Einen (nativen) Thread zu starten nimmt sehr viel Zeit in Anspruch.
Thomas
2.1.1 Antwort: Ingo R. Homann vom: Mittwoch, 29. November 2000
Hi!
Hm, ich dachte eher an etwa folgendes:
Server:
- hat eine Liste von korrespondierenden Input- und Output-Streams, die in einem (einem!) Thread immer aktualisiert wird (d.h. wenn ein neuer Client sich anmeldet, wird die Liste aktualisiert)
- in *einem* weiteren Thread werden (in einer Endlosschleife) immer nach und nach alle InputStreams abgefragt und ggf. auf die Anfragen reagiert.
Client:
- Keine besonderen Aenderungen (evtl. in festen Zeittakten immer mal ein Signal "\n" an den Server schicken, damit dessen readLine() nicht blockiert) ...und natuerlich das flush() nicht vergessen, das hat mich schon sehr oft lange Zeit Fehlersuche gekostet... ;-)
Nachteil:
Ist halt nicht mehr in "Echtzeit", d.h. es kann zu leichten Verzoegerungen kommen (je nach Anzahl der Clients). Aber je nach Anwendungsfall macht das ja evtl. nichts.
Sollte doch grob so funktionieren, oder?
Ciao, Ingo
2.1.1.1 Antwort: Thomas Foerster vom: Mittwoch, 29. November 2000
Stimmt, könnte man so machen (wenn man die Streams zuerst daraufhin prüft, ob blockierungsfrei von ihnen gelesen werden kann). Ob das so schön ist, ist wohl mal wieder *Geschmackssache* :-)
Ich würde die konventionelle Thread-Lösung wählen und ggf. die Client-Anzahl begrenzen oder bessere Hardware beantragen...
Thomas
2.1.1.1.1 Antwort: Jens Tinz vom: Donnerstag, 30. November 2000
Mhmm..
Einen Thread-Pool zu verwenden, und die Anzahl der Verbindungen zu beschraenken, ist eine gute Idee. Wird gemacht. Flushen ist kein Problem. Der konventionelle Server laeuft astrein.
Ich dachte auch daran eine Liste durchzugehen, und zu schauen, ob bei den Streams was im Buffer ist. Allerdings habe ich schlechte Erfahrungen mit InputStream.available(). Gibt's da Alternativen?
Die Verzoegerung ist uebrigens wichtig.
2.1.1.1.1.1 Antwort: Thomas Foerster vom: Donnerstag, 30. November 2000
UDP/IP statt TCP/IP verwenden (mit all den damit verbundenen Nachteilen).
MFG
Thomas
2.2 Antwort: Christoph Dahlen vom: Donnerstag, 30. November 2000
Man kann ja die Anzahl begrenzen. Wenn die maximale eingestellte Verbindungsanzahl überschritten ist, wird die ServerSocket zeitweise zugemacht. Sind wieder Kapazitäten frei, geht's weiter.
Kleines Beispiel:
while(!endsignal) {
Socket s = serverSocket.accept();
if(myThreads.iCounter < MAX_INSTANCE_COUNTER))
new myThreads(s).start();
else
s.close();
}
Deine Thread-Klasse versiehst Du dann mit einer Klassenvariablen (public static iCounter), steckst ein iCounter++ in den Konstruktor und ein iCounter-- in finalize().
Im Beispiel steckt noch viel Potential für Verbesserungen, das "new myThreads(s)" ist furchtbar teuer. Besser ist hier ein ThreadPool. Und obwohl iCounter grösser MAX ist, werden trotzdem noch Verbindungen angenommen. Besser ist es hier ein .accept() Temporär völlig zu unterbinden.
Christoph Dahlen

zur Übersicht

all rights reserved © Bastie - Sebastian Ritter @: w³: http://www.Bastie.de
Diese Seite ist Bestandteil der Internetpräsenz unter http://www.Bastie.de


Java Cobol Software Resourcen Service Links Über mich Zum Gästebuch Forum