Unterschiede
Hier werden die Unterschiede zwischen zwei Versionen angezeigt.
| decoder:code:programmieren-ohne-delay [22.07.2025 12:09] – angelegt Martin Fitzel | decoder:code:programmieren-ohne-delay [Unbekanntes Datum] (aktuell) – Externe Bearbeitung (Unbekanntes Datum) 127.0.0.1 | ||
|---|---|---|---|
| Zeile 1: | Zeile 1: | ||
| + | ====== Programmieren ohne ‚delay‘ ====== | ||
| + | Eines der einfachsten Programme für einen Mikroprozessor ist der „Blink“-Sketch, | ||
| + | |||
| + | // the setup function runs once when you press reset or power the board | ||
| + | void setup() { | ||
| + | // initialize digital pin LED_BUILTIN as an output. | ||
| + | pinMode(LED_BUILTIN, | ||
| + | } | ||
| + | // the loop function runs over and over again forever | ||
| + | void loop() { | ||
| + | digitalWrite(LED_BUILTIN, | ||
| + | delay(1000); | ||
| + | digitalWrite(LED_BUILTIN, | ||
| + | delay(1000); | ||
| + | } | ||
| + | |||
| + | |||
| + | Eine LED wird im Sekunden-Takt ein- und ausgeschaltet, | ||
| + | |||
| + | LED einschalten | ||
| + | 1000 Millisekunden warten | ||
| + | LED ausschalten | ||
| + | 1000 Millisekunden warten … | ||
| + | |||
| + | | ||
| + | |||
| + | Versucht der Programmier-Einsteiger nun, dieses Programm z.B. um weitere LEDs zu erweitern, so stößt er schnell auf die Problematik der Abhängigkeit und erhält auf seine Fragen die lapidare Antwort „schau´ Dir ‚BlinkWithoutDelay an‘ – da ist das Prinzip erklärt“. | ||
| + | |||
| + | Zwar ist m.E. im zugehörigen Tutorial https:// | ||
| + | |||
| + | Anstelle der Befehlskette | ||
| + | |||
| + | Pizza in die Mikrowelle | ||
| + | 10 Minuten warten | ||
| + | Pizza aus der Mikrowelle holen | ||
| + | eMail prüfen | ||
| + | |||
| + | prüft man z.B. alle 2 Minuten die eMails und kommt zu der Befehlskette | ||
| + | |||
| + | Pizza in die Mikrowelle | ||
| + | eMail prüfen | ||
| + | 2 Minuten warten | ||
| + | eMail prüfen | ||
| + | 2 Minuten warten | ||
| + | eMail prüfen | ||
| + | 2 Minuten warten | ||
| + | eMail prüfen | ||
| + | 2 Minuten warten | ||
| + | eMail prüfen | ||
| + | 2 Minuten warten | ||
| + | Pizza aus der Mikrowelle holen | ||
| + | |||
| + | Wenn man sich das bildlich vorstellt, wird schnell klar, dass so niemand arbeitet und dass das spätestens dann nicht mehr funktioniert, | ||
| + | |||
| + | Schon in dem einfachen ‚Blink‘-Programm steht als Kommentar „the loop function runs over and over again forever” – und genau darum geht es: Die Ausführung des Programms nicht anzuhalten, sondern ganz gezielt Befehle auszuführen, | ||
| + | |||
| + | Genau das macht ‚BlinkWithoutDelay‘ nun für die LED – es prüft endlos, ob die Zeit bis zum nächsten Umschalten abgelaufen ist und wenn das Ergebnis „ja“ lautet, wird es ausgeführt: | ||
| + | |||
| + | void loop() { | ||
| + | unsigned long currentMillis = millis(); | ||
| + | if (currentMillis - previousMillis >= interval) { // Zeitintervall abgelaufen ? | ||
| + | previousMillis = currentMillis; | ||
| + | if (ledState == LOW) { // LED umschalten | ||
| + | ledState = HIGH; | ||
| + | } | ||
| + | else{ | ||
| + | ledState = LOW; | ||
| + | } | ||
| + | digitalWrite(ledPin, | ||
| + | } | ||
| + | } | ||
| + | |||
| + | Beim Blinken einer LED sieht man nun leider tatsächlich keinerlei Vorteil – das Programm erscheint dem Einsteiger nur viel unübersichtlicher. Ich habe es daher mal für 5 LEDs an einem ATtiny85 erweitert. Für den Einsatz auf einem Arduino sind natürlich auch mehr als 5 LEDs möglich und die Portnummern anzupassen. Das Programm ist nur unwesentlich größer, kann aber nun 5 LEDs unabhängig mit verschiedenen Frequenzen und unsymmetrisch (High-Low-Verhältnis) blinken lassen, weil pausenlos nacheinander für alle LEDs geprüft wird, ob sie geschaltet werden müssen – das ist mit Verwendung von ‚delay‘ so nicht mehr zu realisieren. | ||
| + | |||
| + | int ledZahl = 5; // Anzahl der LEDs | ||
| + | int ledPin[] = {0, 1, 2, 3, 4}; // Pins der LEDs | ||
| + | unsigned long currentMillis = 0; | ||
| + | unsigned long previousMillis[] = {0, 0, 0, 0, 0}; | ||
| + | int interval[] = {750, 800, 850, 950, 1000}; | ||
| + | int highlowq[] = {5, 5, 5, 2, 2}; | ||
| + | void setup() { | ||
| + | for (int i = 0; i < ledZahl; i++) { | ||
| + | pinMode(ledPin[i], | ||
| + | } | ||
| + | } | ||
| + | void loop() { | ||
| + | currentMillis = millis(); | ||
| + | for (int i = 0; i < ledZahl; i++) { | ||
| + | previousMillis[i] = currentMillis; | ||
| + | digitalWrite(ledPin[i], | ||
| + | } | ||
| + | else if(currentMillis - previousMillis[i] > interval[i]/ | ||
| + | digitalWrite(ledPin[i], | ||
| + | } | ||
| + | } | ||
| + | } | ||
| + | |||
| + | Der prinzipielle Aufbau eines Programms ohne ‚delay‘ unterscheidet sich also grundlegend von Befehlsketten mit ‚delay‘ – und deshalb kann man ein Programm auch kaum „mal eben umschreiben“. Bei der Erstellung eines Programms ist es also sinnvoll, schon von Anfang an möglichst ohne ‚delay‘ zu arbeiten – sowohl um das Prinzip zu lernen, als auch um später bei Erweiterungswünschen nicht wieder komplett von vorne beginnen zu müssen. | ||