Anstatt delay() , millis verwenden für verzögerung!

Lieber Freunde Arduino , wie kann ich anstatt delay() , millis verwenden für verzögerung
in einer while schleife .

danke in voraus

void blinkLed(int pin ,int value){
 
  while (j < value)
 {
    
    
ledState= !ledState;   
    
digitalWrite(pin,ledState);
 j++; 

delay(delayTime); 


// if ((millis()-prev)>= Intervall) {              anstatt delay() , millis  verwenden für verzögerung !!!!!!!!
//   Serial.println(prev);
//   prev= millis();



}
  





void loop(){
 blinkLed(ledPin,wert1 ); 
 
 
   
   }

https://www.norwegiancreations.com/2018/10/arduino-tutorial-avoiding-the-overflow-issue-when-using-millis-and-micros/

Achtung beim C&P, die zweite Lösung ist die korrekte. Und je nach Plattform an yield() denken.

Jan

Wozu?
while() lässt Dich nicht raus, bis die Bedingung erfüllt ist.

Du kannst Dir nen zweiten Funktionsaufruf bauen, abererklä#r doch mal, was Du da willst?
blinken mit while() ist ganz schlecht.

void blinkLed(byte pin , unsigned int value) {
  unsigned long prev = millis();
  bool isOK = true;
  while (isOK)  {
    ledState = !ledState;
    digitalWrite(pin, ledState);

    // anstatt delay() , millis  verwenden für verzögerung !!!!!!!!
    if ((millis() - prev) >= ( (unsigned long)value * 1000)) isOK = false;

  }
}

void loop() {
  blinkLed(ledPin, wert1 );
}

danke für die Hilfe , eigentlich wird nicht ein LED zum blinken gebracht, Text
muss noch geändert werden .Es wird ein StepMotor gesteuert der
nur minimale Bewegungen erfüllen muss, die variable wert1 bekommt werte von eine
Keypad , die Wartezeit benutze ich um den zähler j++ zu inkrementieren

ich habe gezeigt wie du millis() verwenden kannst. was du danach oder daraus machst ist dir überlassen.
ansonsten kann ich nur raten was du zu Stepmotor meinst

Ich denke, Du solltest Dein Konzept überdenken.
Das while() bricht Dir das Genick, spätestens wenn ein weiteres konkurierendes dazu kommt.

danke für die schnelle Hilfe , in diesen kleinen Sketch den ich gepostet kann man nicht delay mit millis() ersetzen?

Doch, aber wozu?

void blinkLed(int pin , int value)
{
  while (j < value)
  {
    digitalWrite(pin, ledState);
    if ((millis() - prev) >= Intervall)
    {
      ledState = !ledState;
      j++;
      prev = millis();
    }
  }
}

Im Übrigen ist das, was Du gepostest hast kein Sketch.
Aber darüber denke ich nach Deinen sonst geheimen Ideen schon nicht mehr nach.

Und nochmal: Bedenke: Das ist ganz grosser Mist.

hast du mein Beispiel nicht gesehen? da gibt's kein delay()

Ja habe ich gesehen und habe mich auch bedankt dafür, in den Fall habe das High - LOW
nur einmal in der Zeit,

es ist immer noch nicht klar ob du lernst Funktionen und denkst dir irgendein Sketch dafür aus oder du hast Gerätschaft und eine bestimmte Vorstellung wie es zusammen arbeiten soll.

Man ersetzt nicht delay() durch millis().
Es ist ein völlig anderes Konzept:
Man schaut sich BlinkWithoutDelay an, und wenn man den Unterschied versteht, weiß man, dass da

  • kein while drin ist
  • ein loop() -Durchlauf keine Zeit braucht
  • das Wesentliche die Zustandsvariable ( z.B. previousMillis ) ist.

Ob man millis() benötigt hängt vom Gesamtprogramm ab.

Nur wenn man im Gesamtprogramm zwei Dinge gleichzeitig machen möchte braucht man millis().

Ob du in diesem Gesamtprogramm millis() wirklich brauchst ist unklar weil du das Gesamtprogramm nicht erklärt hast. Du solltest das Gesamtprogramm in normalen Worten erklären und das Gesamtprogramm als Code posten.

vgs

Was immer Du vorhast, es ist nicht verkehrt, den Umgang mit den "if(millis()-"-Routinen kennengelernt zu haben. Wie @StefanL38 schon schrieb, wo delay() und wo millis() angebracht sind, hängt grundsätzlich von der zu bewältigenden Aufgabe ab.

Man kann aber nahezu alles mit millis() erledigen und ist damit auf jeden Fall flexibler, falls doch noch "quasi-parallele" Aufgaben in einem Projekt auftauchen, und sei es nur das schnelle Reagieren auf serielle Eingaben oder eine Taste ...

Diesen Beispielsketch habe ich schon für eine ähnlich gelagerte Frage erstellt; er zeigt auf, wie man einfach mehrere unterschiedliche Zeitsteuerungen in der loop() realisieren kann. Es gibt jede Menge anderer Lösungen, dies ist nur eine von vielen ...

const byte NoOfTimes = 3;
unsigned long beginToWait[NoOfTimes];
const int wait1s   =  1000;
const int wait3s   =  3000;

boolean TimeIsOver(int Index, unsigned long TimeToWait){
   if(millis()-beginToWait[Index] > TimeToWait) {
          return true;
   } else return false;
}  

void setup(){
  Serial.begin(115200);
  for (int i=0; i< NoOfTimes;i++) beginToWait[i] = 0;
}

void loop(){
    if (TimeIsOver(0, wait1s)){
          // Do something
          Serial.println("Jede Sekunde");
           beginToWait[0] = millis();
   } 
    if (TimeIsOver(1, wait3s)){
          // Do something
          Serial.println("Alle drei Sekunden");
           beginToWait[1] = millis();
   } 
}
1 Like

Danke für die ausführliche Erklärung das finde ich genial, wenn ich stat millis in der Loop Schleife micros() benutze habe ich fast Multikcasting.
Alle Sensoren Input könnten fast im gleichen
Moment Reagieren ,oder gibt es was anderes für Multicast kann das der arduino Controller oder
Muss man stastdessem Threads benutzen

Danke
Salvatore Galipo

Holen Sie sich Outlook für Android

Du meinst sicher "Multitasking" ... Das ist für einen Controller ein vielleicht etwas hoch gestochener Begriff, aber prinzipiell machbar; letztlich entscheiden die Anforderungen der zu bearbeitenden Echtzeitprozesse darüber, ob das sequentielle Bearbeiten eine bemerkbare Rückwirkung hat oder nicht.

Für solche Aufgaben bietet sich vielleicht auf dieser Ebene eher ein ESP32 mit FreeRTOS an, wenn es denn tatsächlich benötigt wird. Die meisten "Hobbyaufgaben" kann man sicher auch sequentiell erledigen.

micros() kann man natürlich auch verwenden; ich gehe aber davon aus, dass es eher selten Aufgaben gibt, bei denen die Auflösung von einer tausendstel Sekunde nicht genügt.

P.S.: Letztlich sind Threads in einem RTOS bei Einkern-Rechnern auch nur (allerdings schön) gekapselte sequentielle Abläufe ... Wie soll es auch anders gehen, wenn es nur einen Rechnerkern gibt ... :wink:

Da verwechselst du was!
Die Dimensionierung eines Zeitrasters sagt nichts darüber aus, ob das jetzt Multitasking ist, oder nicht. Das geht auch ganz ohne Zeitraster.

Mir scheint, du wirfst die Begriffe etwas durcheinander.

Alle scheinbar parallelen Abläufe auf einem Rechner mit nur einem Rechenkern laufen in der Realität sequentiell ab.

In wieweit man das "händisch" mit millis() selbst organisieren darf oder eine Sammlung pfiffiger Task-Makros einem die Arbeit abnimmt oder man gar zu einem Betriebssystem mit Threads und Scheduler greift ist am Ende irrelevant.

Ob wir etwas als "parallel" empfinden, hängt vom jeweiligen Problem ab.
Gleichzeitiges Einschalten von LEDs sollte vielleicht innerhalb 30ms erfolgen, damit die Trägheit des Auges das noch als "gleichzeitig" empfindet, das Schalten von Heizschleifen in einem Druckbett kann möglicherweise im Sekundenbereich erfolgen - das Gesamtsystem ist einfach träge genug.

Danke für den Hinweis.die Frage habe ich gestellt es ist nicht ein Taster den ich abfragen will sonder ein encoder der genau bei eine komplette umdreung 360 Grad abgefragt wird ,da es untereine sequenzielle Bearbeitung läuft,und in den Moment anderen Aktoren im Spiel kommen wenn ich Pech habe werde eine von den nicht Abfragen,oder ich habe den Mechanismus nicht verstanden

Holen Sie sich Outlook für Android