Es gehen nicht alle Zahlen. Kämpfe dich mal durch die verschiedenen Application-Notes.
Besonders heikel ist das beim Vergleichen auf "equal"
Ich berechnen einen Wert mit float Zahlen...
Wenn ich ihn in einen string mit dtostrf wandeln will, gibt es immer einen Rundungsfehler...
Dann wird der Wert 6537.1371 Ausgegeben...Code:char ausgabe[20]; float r=6537.137; dtostrf(r,4,4,ausgabe); disp_text(ausgabe);
auch wenn ich die zahl 6537.13700000 in die Variable schreibe, bringt er mir 6537.13711111111111 ????
Mit der Zahl 6000.2000 funktioniert es tadellos?
Ist für solche Zahlen float nicht geeignet?
Habe auch schon folgendes versucht:
sprintf(ausgabe,"%f",r);
aber da gibt es eine warnung wegen double und ein ? wird ausgegeben...
Irgendwelche Tipps?
Merci
Es gehen nicht alle Zahlen. Kämpfe dich mal durch die verschiedenen Application-Notes.
Besonders heikel ist das beim Vergleichen auf "equal"
mfg robert
Wer glaubt zu wissen, muß wissen, er glaubt.
Ein float wird intern durch 32 Bit repräsentiert, damit sind logischerweise nicht allen reelen Zahlen darstellbar.
Insbesondere gelten -- wie von Robert schon angesprochen -- *nicht* die von den reelen Zahlen vertrauten Rechenregeln!
So ist i.a
a+(b+c) != (a+b)+c
a*(b*c) != (a*b)*c
a*(b+c) != a*b+a*c
etc. und besonders tückisch:
a != b folgt nicht a-b != 0, was zu Laufzeitfehlern beim Dividieren füren kann:
if (a != b)
quot = 1.0 /(a-b); // *AUTSCH*, Divisor kann 0 sein !!!
Weil maximal 2^32 verschiedene reele Zahlen darstellbar sind, gibt es zwischen den Zahlen immer Lücken. Diese Lücken werden um so größer, je größer die darzustellenden Zahlen betragsmässig sind.
Disclaimer: none. Sue me.
Ich versuche immer wenn es irgendwie möglich ist Gleitkommadatentypen zu vermeiden ...
Sie sind neben den den Tücken die SprinterSB genannt hat auch noch sehr langsam!!! (Nicht die Datentypen sondern die Operationen mit ihnen )
mfg
Also Danke mal für die Antworten!
1. Soll das etwa heissen, dass mein ATMEL zu "dumm" ist um diverse Trigonometrische funktionen GENAU auszurechnen?
Das wäre wirklich seeehr schade, da ich an einem GPS-Vermessungsgerät arbeite... Ich kann mir nicht so ganz vorstellen dass dies so ist, da diese Controller in vielen Kundenanwendungen (unserer Kunden) gebraucht werden, die wohl auch um einiges komplexer sind (Funkempfänger mit extrem genauen RSSID Ausgängen).
2. Oder liegt es nur an den Zahlentypen? Kann man da ein anderes Format benutzen?
Huiuiui.... Am Schluss muss ich das noch mit dem PC machen!
Bedenke, daß der AVR nur addieren,subtrahieren,durch 2 dividieren, und mit 2 Multiplizieren kann, das wars.Soll das etwa heissen, dass mein ATMEL zu "dumm" ist um diverse Trigonometrische funktionen GENAU auszurechnen?
Versuche jetzt damit trigonometrische Funktionen zu berechnen.
AVR != x86
Gruß Sebastian
Hallo,
er kann sogar multiplizieren, aber nur zwei 8-bit Ganzzahlen miteinander,
aber dafür mit und ohne Vorzeichen.
Fliesskommazahlen müssen per selbstgebaute Methoden berechnet werden,
denn der AVR selber kann das so nicht.
Zum x86 gibts noch zu sagen, das dieser sogar einen CoPro braucht, wenns genauer werden soll.
Wieso ungenau ? Fließkommazahlen haben die Eigenschaft, einen relativen Fehler zu haben ( abhängig vom gewünschten Zahlenwert ).Soll das etwa heissen, dass mein ATMEL zu "dumm" ist um diverse Trigonometrische funktionen GENAU auszurechnen?
In Deinem Beispiel:
Der relativer Fehler zwischen 6537.13700000 und 6537.13711111111111 ist ungefähr 0.0000001 Prozent. Mit der Genauigkeit kannst Du mit einem Metermaß keine Länge abmessen.
Wenn Du eine größere Genauigkeit brauchst, musst Du von Single Precission auf Double Precission wechseln. Ich weiss allerdings nicht, ob die Double Routinen in der AVR-Lib definiert sind.
Gruss,
stochri
Bist Du Dir sicher ?er kann sogar multiplizieren, aber nur zwei 8-bit Ganzzahlen miteinander,
aber dafür mit und ohne Vorzeichen.
Mit welchem Befehl geht das ?
Soweit ich weiß geht das nur mit Bits linksschieben und da hätte man nur die Zweierpotenzen im Angebot.
Das einzigste mit Vorzeichen wäre dann asr also arithmetisch rechts schieben, aber ich sehe da keinen Zusammenhang.
Ich schau mir nochmal den Befehlsatz an
mit diesem Befehl:
MUL Rd,Rr
ergebnis steht dann in R1:R0
zumindest steht der beim Mega8 mit dabei.
So ein Datenblatt macht schon was her
Lesezeichen