Genauigkeit/Precision ?? (1e-017 = 0 "setzten")
-
Achso, alle Ergebnisse einfach prüfen ob sie kleiner als 0.000...001 sind. Wenn ja den Wert durch 0 ersetzten, wenn nicht lass ich den Wert bestehen!?
Ist das so sinnvoll?
Wenn ich dann mit dem Wert später weiter rechnen muss, ists ja okay, wenn ich mit der 0 rechne...
-
r00t schrieb:
Achso, alle Ergebnisse einfach prüfen ob sie kleiner als 0.000...001 sind. Wenn ja den Wert durch 0 ersetzten, wenn nicht lass ich den Wert bestehen!?
Ist das so sinnvoll?Nein. Der Wert ist in der Regel schon der präziseste, der mit den Eingabedaten und dem Algorithmus errechnet werden kann. Daran nachträglich rumzudoktern würde ich sein lassen. Was otze meint ist speziell auf Vergleiche bezogen. Wenn du z.B. eine Nullstelle einer Funktion suchst, solltest du nicht auf Gleichheit mit Null prüfen, sondern darauf, ob der Wert betragsmäßig kleiner als ein sinnvoll gewähltes Epsilon ist. Das Runden machst du dann erst bei der Ausgabe (sonst kommt sowas raus: http://thedailywtf.com/Articles/55560000000000000002.aspx#Pic2 )
Und lies vielleicht das:
http://download.oracle.com/docs/cd/E19957-01/806-3568/ncg_goldberg.html
oder http://floating-point-gui.de/Das Wählen des richtigen Epsilons ist nämlich ziemlich schwer, wenn man keine Ahnung hat, was man da eigentlich tut.
-
r00t schrieb:
Ich möchte in meinem Programm schon genau rechen. ZBsp hab ich Pi mit 30 Nachkommastellen drin. Weiss zwar auch nicht, ob er da alle Stellen berücksichtigt, wenn ich das als double benutze, aber egal.
Wenn ich verschiedene Berechnungen mache bekomme ich an manchen Stellen -2.3568112e-017. Da hätte ich dann aber gern die 0 stehen.Das ist alles sehr vage. Man kann Dir hier keinen Tipp für die Lösung Deines Problems geben. Um Dir zu helfen, müssten wir entweder wissen, welches Problem Du eigentlich lösen willst, oder wir müssten Dir von Grundauf erklären, wie Fließkommazahlen funktionieren.
Mach Dir klar, dass die Menge der mit per double darstellbaren Zahlen endlich ist (da es nur endlich viele n-Bit-Kombinationen gibt). Bis auf betragsmäßig sehr große und sehr kleine Zahlen wird die Menge so gewählt, dass der Abstand zwischen benachbarten darstellbaren Zahlen annähernd proportional zum Betrag dieser Zahlen ist. Man kann also eine obere Grenze für den relativen Fehler angeben. Das nennt man "Maschinengenauigkeit". Es gibt also für jede reelle Zahl x ein bestimmtes Bitmuster, was eine andere Zahl y = x + e repräsentiert, wobei der relative Fehler e/x betragsmäßig durch die Maschinengenauigkeit beschränkt ist: abs(e/x)<=epsilon. (Mit epsilon ist meist die Maschinengenauigkeit gemeint, so wie auch hier)
Wenn Du jetzt mit den Zahlen rechnest, muss ggf gerundet werden, um wieder etwas zu erhalten, was mit einem double darstellbar wird. Diese Rundungsfehler pflanzen sich natürlich fort. Siehe Einführungskapitel in jedem Numerikbuch.
Wie ein "ist-fast-null-Test" aussehen muss, hängt davon ab, wie sich die Rundungsfehler bis dorthin fortgefplanzt haben. Da fehlt uns jetzt zu viel Information für.
kk
-
Danke für die ganzen Hinweise.
Ich hab jetzt mal wie ich oben vermutet habe weitergemacht (betragsmäßig sehr kleine Werte hab ich mit 0 überschrieben).
Denn - hätte ich vll vorher sagen sollen - muss auch 0 herauskommen und nicht etwa 0 (denke ich zumindest). Sind halt Berechnungen vorher schon zu ungenau/gerundet/oder sowas gewesen...!?
Damit komm ich aber auch bisher gut hin, hab verschiedene Varianten ausprobiert, bis jetzt ohne Komplikationen.
-
r00t schrieb:
Denn - hätte ich vll vorher sagen sollen - muss auch 0 herauskommen und nicht etwa 0 (denke ich zumindest). Sind halt Berechnungen vorher schon zu ungenau/gerundet/oder sowas gewesen...!?
Die Frage versteh ich jetzt nicht genau, aber vielleicht hilft das weiter:
double d03 = 0.3; //ist nicht genau 0.3 double d12 = 1.2; //ist nicht genau 1.2 double d15 = 1.5; //auch nicht genau... double summe = d03+d12; //natürlich nicht 1.5 if (summe == d15) //greift nicht unbedingt.
-
pumuckl schrieb:
double d15 = 1.5; //auch nicht genau...Doch, die schon

-
Bashar schrieb:
Doch, die schon

Gnarf. Ersetze es durch was entsprechend (un-)passendes.
-
Der Fragesteller möchte 30 Nachkommastellen, also mindestens 30 signifikate Stellen einer Gleitkommavariablen. Das passt derzeit in keinen vorbereiteten
Datentyp hinein. Dafür wären andere aufwendigere Massnahmen erforderlich.
-
berniebutt schrieb:
Der Fragesteller möchte 30 Nachkommastellen, also mindestens 30 signifikate Stellen einer Gleitkommavariablen. Das passt derzeit in keinen vorbereiteten
Datentyp hinein. Dafür wären andere aufwendigere Massnahmen erforderlich.Nun, es gibt quadruple precision libraries
. Ich behaupte aber einfach mal, dass der Fragesteller die Frage nach der nötigen Genauigkeit nicht qualifiziert beantworten kann und seine Bedürfnisse weit überschätzt.
-
berniebutt schrieb:
Der Fragesteller möchte 30 Nachkommastellen, also mindestens 30 signifikate Stellen einer Gleitkommavariablen.
Nö. Er hat nur Pi mit 30 Nachkommastellen angegeben. Die Info ist aber garnicht relevant. Sein Problem ist, dass er bei Rechnungen mit double keine exakten Werte bekommt, was einfach das übliche Genauigkeitsproblem mit Fließkommazahlen ist.
-
Ich häng mich mal hier ein, denn ich hab da mal 'ne Frage:
#include <iostream> #include <limits> #include <iomanip> int main() { std::cout<<std::fixed<<std::numeric_limits<long double>::max()<<"\n\n\n" <<std::numeric_limits<long double>::epsilon()<<std::endl; }1. Wieso ist das zweite Ergebniss Null ?
2. Müsste nicht das Verhältniss gelten: größe ersten Wertes geteilt durch 1 ist der Epsilon ?
Also Anzahl möglicher Nachkommastellen gleich Anzahl möglicher 'Vorkommastellen' (ich weiß da gibt es einen Begriff, fällt mir leider grad nicht ein ?
-
1. Weil das epsilon so klein ist, dass du es nicht mit der von dir fixierten Stellenzahl ausgeben kannst, ohne es auf 0 zu runden.
2. Wolltest du "1 geteilt durch" schreiben? Und selbst dann nicht. Du hast den Exponenten vergessen.edit: Schreib doch mal statt fixed scientific (oder lass es weg, da es sowieso Standard ist), dann sollte das klarer werden.
-
SeppJ schrieb:
Weil das epsilon so klein ist, dass du es nicht mit der von dir fixierten Stellenzahl ausgeben kannst, ohne es auf 0 zu runden.
Schafft dieser Datentyp dann also 30 Nachkommastellen ?
Ich würds mit ja ausrechnen, leider weiß ich nicht wie...
Und ja, 1 geteilt durch, das wollt ich schreiben.
-
Hacker schrieb:
Schafft dieser Datentyp dann also 30 Nachkommastellen ?
Wie kommst du auf 30? Kann sein, dass das bei dir so ist, würde mich sehr aber wundern. Und das epsilon hat auch nicht so wirklich was damit zu tun. Beziehungsweise schon, aber nicht so, wie du vermutlich denkst.
-
SeppJ schrieb:
Wie kommst du auf 30?
Wurde im Thread angesprochen.
-
Hacker schrieb:
SeppJ schrieb:
Wie kommst du auf 30?
Wurde im Thread angesprochen.
Es ging darum, dass die Genauigkeit üblicherweise nicht 30 Stellen ist...
-

Eben ?
Da wollt ich wissen ob ein long double diese genauigkeit schafft ...
-
Hacker schrieb:

Eben ?
Da wollt ich wissen ob ein long double diese genauigkeit schafft ...In der Regel nicht, wie du aus dem Wert für das epsilon ablesen kannst, wenn du fähig wärst, es dir anzeigen zu lassen. Dass hier bei dir nichts erscheint, liegt nicht da dran, dass der Wert an sich zu klein ist für die Anzeige, sondern dass du nicht genau weißt, was du da mit den Streammanipulatoren getan hast.
-
Ahh, sry. Ich hab setprecision vergessen. Jetz seh ich's.
Edit: Nein, immer noch falsch. Es scheint, als ob long double (edit) ca. 80 Nachkommastellen schafft.
-
Hacker schrieb:
Ahh, sry. Ich hab setprecision vergessen. Jetz seh ich's.
Edit: Nein, immer noch falsch. Es scheint, als ob long double 63 Nachkommastellen schafft.
Wenn du nicht an einem Spezialrechner sitzt, dann ist auch das Unsinn. Wie kommst du auf die Werte?