![]() |
AW: Hauptthread splitten und wieder zusammenführen
Es gibt ja noch dieses unsägliche (uh, ich trau es mir kaum zu sagen)....goto :duck:
![]() Ich hab jetzt aber nicht gesagt, dass man es benutzen soll :) Aber es wäre wohl eine Möglichkeit...wenn auch eine ziemlich gefährliche / unschöne. Der beste Weg wäre doch aber wohl der, komplett alles Event-gesteuert zu machen, so dass es eben gar nichts gibt, was nach dem Funktionsaufruf "weiterläuft". Wenn alle Threads fertig sind, wird im Hauptthread ein Event gefeuert und dieser zeigt die Berechnungen dann an. Was spricht denn da dagegen? |
AW: Hauptthread splitten und wieder zusammenführen
Zitat:
und das hab ich dann natürlich auch wörtlich genommen :stupid: |
AW: Hauptthread splitten und wieder zusammenführen
Google mal nach OmniThreadLibrary, die bietet fortgeschrittene Threadfunktionen (Join, Future uvm.) und ist relativ einfach in der Vewendung.
|
AW: Hauptthread splitten und wieder zusammenführen
Okay, stellt such vor, ich habe eine neue "InttoStr" (oder irgend eine andere Funktion, die ihr überall in euren Programmen verwendet) Funktion geschrieben, die durch Multithreading schneller arbeitet. (Und stellt euch vor, die Funktion braucht selbst mit Multithreading 1-2 Sekunden Bearbeitungszeit. Läuft der Hauptthread einfach weiter, ist das Ergebnis noch gar nicht berechnet worden. Bleibt er per Semaphore stehen, steht auch das Programm und es können keine Synchronizes mehr ausgeführt werden.
Ein "Auffang-" Event bringt hier nicht viel. Weil der Aufruf an x beliebigen Stellen im Programm erfolgt, auf den x verschiedene Abläufe folgen. Stellt euch den nachfolgenden Code, als Black-Box vor. Ich gebe euch meine "neue" InttoStr Funktion und ihr könnt die in euren Programmen verwenden, ohne euren Quelltext verändern zu müssen. Ich habe das Problem jetzt (vorübergehend) mit Polling gelöst. @mjustin Danke, werde es mir bei Gelegenheit zu Gemüte führen. |
AW: Hauptthread splitten und wieder zusammenführen
Hallo,
ich weiß nicht ob dich das Weiter bringt, oder ob das Performanter ist, aber es ist zumindest mehr OnDemand was das Application.ProcessMessages angeht :-) Also: 1. Funktion MyIntToStr erzeugt Threads. 2. Es wird in einem Array die gleiche Anzahl an TEvents erzeugt. 3. Thread hat z.B. ein TEvent property. Zuweisung mit den TEventArray. 4. Jeder Thread löst das TEvent aus am ende von seiner Execute-Methode. 5. Funktion MyIntToStr erzeugt sich ein HandleArray aller Events 6. Warten auf das Ende mittels:
Delphi-Quellcode:
Man könnte hier auch noch zusätzlich ein Abbruch Event hinein bringen. Aber das überlasse ich anderen :-)
doneCount := 0;
doneMax := length(TheHandleArr); repeat Erg := MsgWaitForMultipleObjects(doneMax, @TheHandleArr[0], FALSE, INFINITE, QS_ALLINPUT); if (Erg < WAIT_OBJECT_0) or (Erg > WAIT_OBJECT_0 + doneMax -1) then begin Application.ProcessMessages; if Application.Terminated then Exit; end else begin inc(doneCount); end; until doneCount = doneMax Vielleicht hilft es ja. Greez, Chris |
AW: Hauptthread splitten und wieder zusammenführen
Mit WaitFor wartet man auf das Ende ... es gibt aber noch andere Möglichkeiten, um rauszubekommen, ob ein Thread schon fertig ist.
(z.B. mit Christians Events) Wie startets du eigentlich die vielen Threads? Eventuell kann man da einiges Zusammenfassen und mit in die Klasse einbauen, damit du es überall einfach aufrufen kannst.
Delphi-Quellcode:
Wenn das Starten einheitlich ist, dann läßt sich alles in eine Start-Funktion des TMyThread verlagen.
X := TMyThread.Create;
Y := TMyThread.Create; Z := TMyThread.Create; repeat Sleep(10); Application.ProcessMessages; until X.istFertig and Y.istFertig and Z.istFertig; X.Free; Y.Free; Z.Free; //weiter gehts...
Delphi-Quellcode:
class procedure TMyThread.Warte(MyThreads: array of TMyThread);
var b: Boolean; i: Integer; begin repeat Sleep(10); Application.ProcessMessages; B := True; for i := High(MyThreads) downto 0 do if not MyThreads[i].istFertig then begin B := False; Break; end; until B; for i := High(MyThreads) downto 0 do MyThreads[i].Free; end; SetLength(X, 3); X[0] := TMyThread.Create; X[1] := TMyThread.Create; X[2] := TMyThread.Create; TMyThread.Warte(X);
Delphi-Quellcode:
class procedure TMyThread.Starte(Parameter...);
var MyThreads: array of TMyThread; b: Boolean; i: Integer; begin SetLength(MyThreads, 3); for i := 0 to High(MyThreads) do MyThreads[i] := TMyThread.Create(Parameter...); repeat Sleep(10); Application.ProcessMessages; B := True; for i := High(MyThreads) downto 0 do if not MyThreads[i].istFertig then begin B := False; Break; end; until B; for i := High(MyThreads) downto 0 do MyThreads[i].Free; end; TMyThread.Starte(Parameter...); |
AW: Hauptthread splitten und wieder zusammenführen
Hmmm...
Eure Antworten sagen mir, dass ihr auch keine bessere Lösung als Polling kennt. Selbst die Bücher, die ich bisher konsultiert habe schlagen Polling vor. Also ist es Polling. Meine Umsetzung ist ähnlich eurer. Nur verwende ich den WorkerThreadPool und warte in ner Schleife darauf, dass die PendingJobs bei 0 ankommen. Danke |
AW: Hauptthread splitten und wieder zusammenführen
die MsgWaitForMultipleObjects-Variante pollt nicht!
(für eine Beschreibung dieser Variante, ließ dir mal die Infos zum ![]() Dann gibt es noch die Möglichkeit, über OnTerminate der Threads sich über deren Ende informieren zu lassen, bzw. ich würde dort die Events für's MsgWaitForMultipleObjects setzen lassen, falls man eigene Events nutzen möchte. |
AW: Hauptthread splitten und wieder zusammenführen
Zitat:
Bei der Abarbeitung einer Message soll er einerseits "anhalten und abwarten" und andererseits "andere Nachrichten abarbeiten" ... :roll: Wenn Multithreading und Parallelisierung so einfach wären, hätte es jeder schon längst gemacht. Aber bei sequentiellen programmiersprachen muss man eben ein bisschen was ändern. P.S.: ichhab gehört, in Prism geht sowas relativ leicht. Aber auch da muss man vorher nachdenken und man bekommt das ergebnis nicht vor der Rechnung. |
Alle Zeitangaben in WEZ +1. Es ist jetzt 13:39 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz