Probleme mit unsigned long berechnung

Hallo Zusammen,

stehe vor einem Rätzel. Ich versuche eine Abfrage zu schreiben, welche zu jeder vollen Minute etwas macht.

Meine Idee war es einen unsigned long zu definieren, auf den die fehlenden Sekunden aufaddiert werden und dann mit millis() verglichen wird.

Der long setzt sich folgender Maßen zusammen:

timeToUpdate = millies() + ((60 - seconds) * 1000);

seconds wiederrum wird auf einer RTC via i2c bezogen

void getTimeFromRTC() {
  Wire.beginTransmission(realTimeClock);
  Wire.write(0);
  Wire.endTransmission();
  Wire.requestFrom(realTimeClock, 7);
  seconds     = bcdToDec(Wire.read());
  minutes     = bcdToDec(Wire.read());
  hours       = bcdToDec(Wire.read());
  dayOfWeek  = bcdToDec(Wire.read());
  dayOfMonth = bcdToDec(Wire.read());
  month      = bcdToDec(Wire.read());
  year       = bcdToDec(Wire.read());
}

byte bcdToDec(byte val) {
  // Convert binary coded decimal to normal decimal numbers
  return ( (val / 16 * 10) + (val % 16) );
}

Die Sekunden werden richtig erhalten, wenn ich die Anzeige interessant ist nur, das nur secunden größer 33 richtig berechnet werden alles darunter gibt wirre zahlen (444221234 z.B.).

Der Vergleich selber greifft, wenn dir Zeit richtig berechnet wird sprich wenn Secunden größer 33 sind.

Leider kapiere ich nicht wo der Fehler steckt. Ich hoffe das ich alle Infos die benötigt werden geliefert habe, wenn nein schreibe ich gerne das Fehlende…

Danke schon mal

Steve

Korrekt:

timeToUpdate = millis() + ((60 - seconds) * 1000*UL*);

Du musst bei der Multiplikation auch unsigned long angeben. Sonst wird in int gerechnet und da bekommst du dann wie du bemerkt hast einen Überlauf bei etwas über 32000

ich vermute mal das der compiler mit millies() nichts anfangen kann versuch es mal mit millis()

Super funktioniert, nur verstehen tu ich es leider nicht....

Warum bekomme ich denn den Überlauf?

(millies hatte ich mich verschrieben, ist im Programm aber richtig gewesen)

Warum bekomme ich denn den Überlauf?

Konstanten sind in c/C++ immer int. Wenn du sie als Long betrachtet haben möchtest, musst du das dem Compiler mitteilen.

Ah ok, un das das dann mit 30 sekunden ging war dann zufall?

Es geht um (60 - seconds) * 1000 Der Standard-Datentyp ist signed int. Wenn du nichts angibst wird damit gerechnet

Anders wäre es z.B. wenn seconds schon ein unsigned long wäre. Dann sollte es wieder gehen. Es muss nur einer der Datentypen unsigned long sein. Dann wird auch in unsigned long gerechnet.

Ah ok, un das das dann mit 30 sekunden ging war dann zufall?

Nein. Überhaupt nicht. Der Maximal-Wert eines signed int ist 2^16 / 2 - 1 = 32767 (oder 2^15 - 1)

EDIT: Korrektur. - 1 vergessen

Ah ok nun macht das auch für mein Anfängerhirn Sinn :D Danke :roll_eyes: