hochauflösender Delay()

Für allgemeine Fragen zur Programmierung mit PureBasic.
SBond
Beiträge: 266
Registriert: 22.05.2013 20:35

hochauflösender Delay()

Beitrag von SBond »

Hi Leute,

gibt es eine einfache Möglichkeit einen hochauflösenden Delay zu erstellen?

Delay(1) ist zu langsam
Delay(0) ist zu schnell.

ich möchte damit einen Thread steuern, um die Verarbeitung von Daten zu regulieren.


viele Grüße,
SBond
41 6c 73 6f 20 77 65 6e 6e 20 64 75 20 73 6f 20 76 69 65 6c 20 4c 61 6e 67 65 77 65 69 6c 65 20 68 61 73 74 2c 20 64 61 6e 6e 20 6b 61 6e 6e 73 74 20 64 75 20 61 75 63 68 20 67 6c 65 69 63 68 20 7a 75 20 6d 69 72 20 6b 6f 6d 6d 65 6e 20 75 6e 64 20 61 62 77 61 73 63 68 65 6e 2e

:D
Benutzeravatar
NicTheQuick
Ein Admin
Beiträge: 8812
Registriert: 29.08.2004 20:20
Computerausstattung: Ryzen 7 5800X, 64 GB DDR4-3200
Ubuntu 24.04.2 LTS
GeForce RTX 3080 Ti
Wohnort: Saarbrücken

Re: hochauflösender Delay()

Beitrag von NicTheQuick »

Hm... Das klingt irgendwie nicht so als ob du das Problem korrekt angehst. Kannst du etwas genauer erzählen welche Daten da verarbeitet werden sollen?
Benutzeravatar
_sivizius
Beiträge: 98
Registriert: 23.10.2013 15:21

Re: hochauflösender Delay()

Beitrag von _sivizius »

du könntest den Inline-Assembler nutzen und mit

Code: Alles auswählen

NOP ; No-Operation
das fein abpassen.
Benutzeravatar
STARGÅTE
Kommando SG1
Beiträge: 7032
Registriert: 01.11.2005 13:34
Wohnort: Glienicke
Kontaktdaten:

Re: hochauflösender Delay()

Beitrag von STARGÅTE »

Code: Alles auswählen

Global QueryPerformanceFrequency.q, QueryPerformanceFactor.f
QueryPerformanceFrequency_(@QueryPerformanceFrequency)
QueryPerformanceFactor = 1e6/QueryPerformanceFrequency

Procedure DelayMicroSeconds(Time.q)
   Protected StartTime.q, EndTime.q
   QueryPerformanceCounter_(@StartTime)
   Repeat
      Delay(0)
      QueryPerformanceCounter_(@EndTime)
   Until (EndTime-StartTime)*QueryPerformanceFactor > Time
EndProcedure



a = ElapsedMilliseconds()
For n = 1 To 1000
   DelayMicroSeconds(300)
Next
Debug ElapsedMilliseconds()-a

PB 6.01 ― Win 10, 21H2 ― Ryzen 9 3900X, 32 GB ― NVIDIA GeForce RTX 3080 ― Vivaldi 6.0 ― www.unionbytes.de
Aktuelles Projekt: Lizard - Skriptsprache für symbolische Berechnungen und mehr
SBond
Beiträge: 266
Registriert: 22.05.2013 20:35

Re: hochauflösender Delay()

Beitrag von SBond »

danke erstmal ;)

eingentlich ist die frage ganz allgemein gemeint. In meinem aktuellen Fall lese ich über den seriellen Port Daten ein und übertrage dies einem großen Ringpuffer. Das ganze geht in einem Thread. Damit der Thread die CPU nicht so stark belastet nutze ich ein Delay um ihn abzubremsen oder um den Füllstand des COM-Puffers zu regeln.

Der Delay ist in meinem Fall aber nicht so krittisch, da auch ein Delay von 10ms noch ok ist.

-----------------------------------------------

Aber mal ganz allgemein....
Nehmen wir mal an, ich habe eine Prozedur die 5000 mal pro Sekunde ausgeführt werden soll. Die Ausführung soll gleichmäßig sein. Das heißt, ich will die Prozedur nicht in den ersten 100ms 5000 mal aufrufen und dann 900ms pausieren, sondern die Prozedur alle 200µs aufrufen.

...eventuell wird es so deutlicher:

Code: Alles auswählen

Counter = 0
Timer	= ElapsedMilliseconds()

While ElapsedMilliseconds() - Timer <= 1000
	Counter + 1
Wend
Debug "Messung 1: " + Str(Counter)

; ############################################

Counter = 0
Timer	= ElapsedMilliseconds()

While ElapsedMilliseconds() - Timer <= 1000
	Counter + 1
	Delay(0)
Wend
Debug "Messung 2: " + Str(Counter)

; ############################################

Counter = 0
Timer	= ElapsedMilliseconds()

While ElapsedMilliseconds() - Timer <= 1000
	Counter + 1
	Delay(1)
Wend
Debug "Messung 3: " + Str(Counter)
Mit Delay(1) erreicht der Zähler nach einer Sekunde den Wert von ca. 1000.
Ohne Delay erreicht der Zähler nach einer Sekunde den Wert von ca. 5,2 Millionen.

Was muss ich machen, wenn ich z.B auf 10000 hochzählen möchte ohne dass ich die CPU unnötig belaste. Alse so etwas wie ein: Delay(0.1), den es ja nicht gibt.


...ich bin schlecht in veranschaulichen. vergebt mir :mrgreen:

----------------------------------------------------------
EDIT: hoppla.... da war einer schneller :) DelayMicroSeconds ist genau das richtige :)
41 6c 73 6f 20 77 65 6e 6e 20 64 75 20 73 6f 20 76 69 65 6c 20 4c 61 6e 67 65 77 65 69 6c 65 20 68 61 73 74 2c 20 64 61 6e 6e 20 6b 61 6e 6e 73 74 20 64 75 20 61 75 63 68 20 67 6c 65 69 63 68 20 7a 75 20 6d 69 72 20 6b 6f 6d 6d 65 6e 20 75 6e 64 20 61 62 77 61 73 63 68 65 6e 2e

:D
Benutzeravatar
Thorium
Beiträge: 1722
Registriert: 12.06.2005 11:15
Wohnort: Germany
Kontaktdaten:

Re: hochauflösender Delay()

Beitrag von Thorium »

Für alles unter 1ms nutzt man QueryPerformanceCounter. Damit kannst du die Zeit messen. Ein genaues Steuern ist nicht möglich. Du befindest dich in einem Multitaskingsystem und wieviel CPU Zeit dir wann zugesprochen wird ist kaum beeinflussbar.

Sollte eine genauere Syncronisation mit Peripherie nötig sein musst du ein Echtzeitsystem einsetzen. Oder noch nen Controller dazwischen setzen.

Alles unter Delay(1) lasstet die CPU aus. Das liegt am OS, was keine genauere Steuerung zulässt. Allerdings ist das auch kein wirkliches Problem.
Zu mir kommen behinderte Delphine um mit mir zu schwimmen.

Wir fordern mehr Aufmerksamkeit für umfallende Reissäcke! Bild
Antworten