![]() |
Delay(sleep) nicht synchron,gegenseitige Blockade
wenn man dieses Delay Funktion von Hagen verwendet, geht die Synchronität verloren, gibts denn da eine Möglichkeit, das trotzdem zu realisieren?
![]() wenn man Button1 drückt, und gleich darauf Button2 ... dann kehrt Button1 erst zurück, NACHDEM Button2 fertig ist, obwohl in Button1 nur 1000 msec Verzögerung angegeben ist, gegenüber 10 Sekunden bei Button2 ....
Delphi-Quellcode:
procedure Delay(Milliseconds: Integer);
var Tick: DWord; Event: THandle; begin Event := CreateEvent(nil, False, False, nil); try Tick := GetTickCount + DWord(Milliseconds); while (Milliseconds > 0) and (MsgWaitForMultipleObjects(1, Event, False, Milliseconds, QS_ALLINPUT) <> WAIT_TIMEOUT) do begin Application.ProcessMessages; if Application.Terminated then Exit; Milliseconds := Tick - GetTickcount; end; finally CloseHandle(Event); end; end; //============================================================================== procedure TForm2.Button1Click(Sender: TObject); begin sleepX(1000); ShowMessage('Button1'); end; //============================================================================== procedure TForm2.Button2Click(Sender: TObject); begin sleepX(10000); ShowMessage('Button2'); end; //============================================================================== |
Re: Delay(sleep) nicht synchron,gegenseitige Blockade
Du kannst das Problem mit 2 separaten Threads lösen:
Delphi-Quellcode:
function m1(arg:pointer):DWORD;stdcall;
begin sleep(2000); MessageBox(form1.Handle,'','',MB_OK); result:=0; end; function m2(arg:pointer):DWORD;stdcall; begin sleep(5000); MessageBox(form1.Handle,'','',MB_OK); result:=0; end; procedure TForm1.Button1Click(Sender: TObject); id:cardinal; begin CreateThread(nil, 0, @m1, nil, 0, id); end; procedure TForm1.Button2Click(Sender: TObject); id:cardinal; begin CreateThread(nil, 0, @m2, nil, 0, id); end; |
Re: Delay(sleep) nicht synchron,gegenseitige Blockade
Stell dir folgende Geschichte vor:
Zitat:
In deinem Beispiel tritt ein vergleichbares Problem auf: durch Aufruf von Application.ProccessMessages werden Mausklicks und Tastatureingaben sofort bearbeitet und die aktuelle Funktion (Delay()) solange unterbrochen. In einer richtigen Anwendung würde man einfach die meisten Buttons (oder besser Actions) ausschalten (.Enabled := False) bis der Vorgang angeschlossen ist. Das wäre die sauberste Lösung denn der Benutzer sieht schon optisch, dass die Anwendung beschäftigt ist und keine neuen Befehle annehmen kann. Andere Möglichkeit: Innerhalb von Delay() statt Application.ProcessMessages nur die notwendigen Paint-Messages verarbeiten. |
Re: Delay(sleep) nicht synchron,gegenseitige Blockade
@new32 .. Thread wäre komplett falsch, es geht um Warte und Synchronisationsprobleme, es geht quasi darum, dass die Button1Click Procedure wirklich mit der Ausführung wartet. (auf gewisse Zustände des programmes / Flags) nur im Hauptthread. Eventuell sogar mit Threads dazu, da läuft was noch nicht rund.
Anwendung der Delay funktion wäre dann folgende:
Delphi-Quellcode:
While not Flag do
Delay(50); @shmia ... die Button Anwendung ist nur ein Beispiel ... ich hab aber schon ungefähr eine grobe Vorstellung, wie es gehen müsste. Die schleife für app.processmessages dürfte nur einmal laufen, und müsste ein Array aller procedure Eintritte prüfen, damit sowas parallel laufen kann .. ist mir aber noch nicht ganz klar, wie das gehen soll, und ob das wirklich funktioniert |
Re: Delay(sleep) nicht synchron,gegenseitige Blockade
ich glaube, das geht wirklich nicht .. Mißt .. :(
Da ja Button1 dann eigentlich im Aufrufstack hängt und unterbrochen wird. und somit die Button2click eigentlich in der Button1click procedure ausgeführt wird und Button1click keine Chance hat, eher zurückzukehren, als Button2click ... blöd .. aber ist halt eben nur ein Thread :) |
Re: Delay(sleep) nicht synchron,gegenseitige Blockade
Erzähl mal was dein Programm eigentlich tun soll.
Es gibt ja noch andere Möglichkeiten wie z.B. eine Liste mit Elementen. Jedes Element enthält einen Zeitpunkt und einen "Aktionscode". Wenn man neue Elemente in die Liste einfügt wird diese gleich wieder nach aufsteigenden Zeitpunkten sortiert. Ein Dispatcher-Funktion sorgt dann dafür, dass wenn die kleinste Zeit erreicht wird, das Element aus der Liste genommen und die Aktion ausgeführt wird. |
Re: Delay(sleep) nicht synchron,gegenseitige Blockade
Zitat:
Die Lösung kann eigentlich nur sein, alles was nach dem Delay kommt in eine eigene Procedure auszulagern und anstatt dem Delay einen Timer (oder etwas ähnliches) zu aktivieren, der dann die "ausgelagerte" Procedure aufruft. Gruß Olli |
Re: Delay(sleep) nicht synchron,gegenseitige Blockade
Zitat:
es geht wahrscheinlich dann nur über eine "ausgelagerte" Procedure, wie Olli vorgeschlagen hat. Die Idee mit dem Aktionscode ist interessant, wobei ich mir noch überlege, ob das für mein Problem relevant ist. Aber merken werde ich es mir auf alle Fälle.. Ich hatte eigentlich ein anderes Problem, wo das Delay in Zusammenarbeit mit Threads nicht funktioniert, ich dachte fälschhlicherweise, wenn ich erstmal das heruntergebrochene Delay-Problem gelöst habe, kann ich mein ursrpüngliches Problem lösen.. eigentlich war das gar nicht das Hauptproblem .. Es trat das Probelem auf, dass im Delay Aufruf auf ein Flag gewartet wird, welches auf einen zweiten Thread wartet ... bzw. der zweite Thread setzt das Flag ... nicht direkt, sondern per Synchronize. Aber komischwerweise wartet der Thread nun auch, bis delay fertig ist, und hat nicht die Möglichkeit das Flag zwischendurch zu setzen, schon komisch ... Der Synchronize aufruf geht eben wahrscheinlich nicht über die Nachrichtenwarteschleife des PRogramms ... Der Vorschlag von Olli ist dann wahrscheinlich das, was ich brauche. Oder eventuell umständliche Joblisten mit Objekt zwischenkopien. Im Moment noch etwas ratlos bin .. |
Re: Delay(sleep) nicht synchron,gegenseitige Blockade
Bitte auch immer Beitrag 17
![]() Wie shmia schon sagte, muss dein PRoblem auch anders zu lösen sein. Daz müssen wir aber erstmal das Problem kennen. |
Alle Zeitangaben in WEZ +1. Es ist jetzt 04:49 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