Double ungenau

papabaer1707

Aktives Mitglied
Ich möchte ein Programm schreiben (Konsole), welches eine Wertetabelle für eine Funktion ausgibt (hier x²). Startwert, Endwert und Schrittweite sollen eingegeben werden. Alle Variablen wurden als double gekennzeichnet - als Ergebnis bekomme ich dies (siehe Bild).

Java:
public class wertetabelle {
  public static void main(String[] args) {
    double startwert;
    double endwert;
    double schrittweite;
    double funktionswert;

    System.out.print("Gib den Startwert ein: ");
    startwert = Input.readDouble();
    System.out.print("Gib den Endwert ein: ");
    endwert = Input.readDouble();
    System.out.print("Gib die Schrittweite ein: ");
    schrittweite = Input.readDouble();
    
    for (double i = startwert; i <= endwert; i += schrittweite) {
      funktionswert = i*i;
      System.out.println("\t " + i + "\t | " + funktionswert);
    }
  }
}

Weshalb gibt es diese Ungenauigkeiten? Wie kann ich das abstellen?
 

Anhänge

  • double.jpg
    double.jpg
    85,8 KB · Aufrufe: 111

W9ND3R

Aktives Mitglied
Allgemein:
Der Typ double ist eine Gleitkommazahl mit einer Größe von 8 Byte. Die Genauigkeit liegt bei 15 Nachkommastellen

Hier was aus der JavaInsel dazu.

Ansonsten kannst auch noch BigDecimal-Werte verwenden, wenn du die Genauigkeit sichern willst. Dazu hier die API.
Gruß.
 

papabaer1707

Aktives Mitglied
Hm, wenn ich aber von -5 bis 5 je 0.2 addiere dürfte das die Genauigkeit nicht überbeanspruchen ...

Mir würden aber z. B. 5 Nachkommastellen genügen ... mit ROUND kann ich das erledigen. Mich interessiert aber, weshalb er diese Abweichungen hat.
 

Marco13

Top Contributor
Gleichzeitig.
Das Problem ist, dass bestimte Zahlen mit double einfach nicht genau dargestellt werden können, so wie z.B. 1/3 im dezimalsystem nicht genau dargestellt werden kann, sondern nur als 0.3333333333333333333333333333333333333333.... Siehe auch Gleitkommazahl ? Wikipedia und hunderte(!) Forenbeiträge hier.
 

Ark

Top Contributor
Weshalb gibt es diese Ungenauigkeiten? Wie kann ich das abstellen?
Gleitkommazahlen sind prinzipiell ungenau, und eine der Ungenauigkeiten im Umgang mit Dezimalzahlen ist mit ihrer Basis begründet: Dezimalzahlen (das sagt schon das Wort) haben die Basis 10, Binärzahlen haben die Basis 2. Da double und float zu Letzterem gehören, können sie nur Zahlen exakt aufnehmen, deren Binärdarstellung endlich und auf eine bestimmte Anzahl von Binärziffern (bei double höchstens 53, bei float höchstens 24) begrenzt ist.

Die Zahl 0.2 zur Basis 10 hat aber zur Basis 2 eine unendliche periodische Ziffernfolge, deswegen können weder float noch double diese Zahl verlustfrei aufnehmen.

"Abstellen" in dem Sinne kann man das nicht. Man kann nur anders rechnen (z.B. mit anderer Skalierung, gemeinen Brüchen oder Implementierungen wie BigDecimal) oder, wenn das erlaubt und möglich ist, intern mit diesen Fehlern weiterrechnen und lediglich zur Anzeige auf passende Genauigkeiten runden.

Ark
 

papabaer1707

Aktives Mitglied
OK, schönen Dank, ich denke, ich bin im Bilde ...

Habs jetzt so gelöst ...

Java:
    System.out.printf("%10s |%10s%n" , "x-Wert", "y-Wert");
    System.out.println("------------------------");
    for (double i = startwert; i <= endwert; i += schrittweite) {
      funktionswert = i*i;
      System.out.printf("%10.2f |%10.2f%n" , i, funktionswert);
    }
 
Zuletzt bearbeitet:

Andi_CH

Top Contributor
Lässt sich das Folgende auch irgendwie erklären?

10.0 "beliebig" genau
0.2 ist auch "beliebig" genau

und doch zeigt sich schon nach der zweiten Substraktion eine Abweichung die viel grösser als zu erwarten ist obwohl auch der Wert 9.6 "beliebig" genau dargestellt werden kann, wie unten gezeigt wird.

PS: bitte nicht über "beliebig" diskutieren :) damit möchte ich nur sagen, dass es viel genauer als die Abweichung ist.

Java:
String format = "%5.100f";
double d1 = 10.0;
double d2 = 0.2;
System.out.println(String.format(format, d1));
System.out.println(String.format(format, d2));
for (int i=0; i<5; i++) {
	d1 -= d2;
	System.out.println(i + " : " + String.format(format, d1));
}
d1 = 9.6;
System.out.println(String.format(format, d1));

Output:
Code:
10.0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
0.2000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
0 : 9.8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
1 : 9.6000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000
2 : 9.4000000000000020000000000000000000000000000000000000000000000000000000000000000000000000000000000000
3 : 9.2000000000000030000000000000000000000000000000000000000000000000000000000000000000000000000000000000
4 : 9.0000000000000040000000000000000000000000000000000000000000000000000000000000000000000000000000000000
9.6000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
 

tfa

Top Contributor
0.2 ist auch "beliebig" genau
Im Binärsystem ist 0.2 ein periodischer Dezimalbruch, und damit (intern) nicht beliebig genau. (Wenn ich mich nicht verrechnet habe ist 0,2=0,00101001010010100101...).
Den Fehler sieht man erst, wenn er durch Berechnungen angehäuft hat. Du kannst in deinem Test d2 ja mal den Wert 0,03125 geben. Diese Zahl kann man im Binärsystem exakt darstellen.
 

tfa

Top Contributor
Der Ausgabe-Algorithmus rundet ja auch bzw. benutzt eine gerundete Darstellung. Und am Anfang ist der Unterschied zum exakten Wert eben zu gering, um aufzufallen.

Die Wahrheit kannst Du so zu Tage fördern:

Java:
System.out.println(Long.toBinaryString((Double.doubleToLongBits(0.2))));
System.out.println(Long.toBinaryString((Double.doubleToLongBits(0.03125))));
liefert
11111111001001100110011001100110011001100110011001100110011010
11111110100000000000000000000000000000000000000000000000000000
(Hab mich oben wohl doch verrechnet)
 

Marco13

Top Contributor
Signifikante Stellen:
double d2 = 12345e-50;
->
0,0000000000000000000000000000000000000000000001234500000000000000000000000000000000000000000000000000
 

Andi_CH

Top Contributor
Hm es muss die 16. Stelle sein.

Code:
1.0/3.0   = 0.3333333333333333000000000000000
1.0/3.0   = 0.6666666666666666000000000000000
100.0/3.0 = 33.333333333333336000000000000000
 
Zuletzt bearbeitet:
Ähnliche Java Themen
  Titel Forum Antworten Datum
Y Datentypen Double Division ungenau Java Basics - Anfänger-Themen 45
B Datentypen Multiplzieren mit double wird ungenau Java Basics - Anfänger-Themen 4
W Double or Float zusammenrechnen Java Basics - Anfänger-Themen 15
I Review von euch erwünscht, double Rechnung falsch Java Basics - Anfänger-Themen 34
X wie bekomme ich durch Eingabeaufforderung definierte double in einen Befehl, welcher 3 erwartete double braucht? Java Basics - Anfänger-Themen 3
Avalon String in Double bzw. Währung konvertieren Java Basics - Anfänger-Themen 6
MoxMorris Integer.MAX_VALUE und Double.MAX_VALUE Unterschied Java Basics - Anfänger-Themen 3
krgewb Double mit zwei Nachkommastellen Java Basics - Anfänger-Themen 2
B Produkt eines double - streams Java Basics - Anfänger-Themen 3
Lion.King Fehler in double und int Java Basics - Anfänger-Themen 7
F java: incompatible types: possible lossy conversion from double to int Java Basics - Anfänger-Themen 1
J Double Variable und Addition Java Basics - Anfänger-Themen 2
F Double Ausgabe nicht wissenschaftlich Java Basics - Anfänger-Themen 16
S Fragen zu Ausgabe double und float Java Basics - Anfänger-Themen 3
Kotelettklopfer Variablen Double zwingen Ganzzahlen mit 2 Nachkommastellen auszugeben Java Basics - Anfänger-Themen 10
A possible lossy conversion from double to int Java Basics - Anfänger-Themen 5
I Output BigDecimal anstatt double / Problem beim Rechnen Java Basics - Anfänger-Themen 16
L ArrayList<String> --> double[] array Java Basics - Anfänger-Themen 18
FelixN Array mit verschiedene Datentypen als Rückgabewert? (Long und Double) Java Basics - Anfänger-Themen 3
J Transformation zweier Integer in ein Double Java Basics - Anfänger-Themen 26
N The method setSaldo(double) in the type Konto is not applicable for the arguments (int, int) Java Basics - Anfänger-Themen 2
C Konvertierung des int typs in den double typ für die Ausgabe mit Nachkommastellen Java Basics - Anfänger-Themen 4
V Erste Schritte Die Nuller bei double NICHT abschneiden Java Basics - Anfänger-Themen 4
L Datentypen Rechnen und abrunden mit double Java Basics - Anfänger-Themen 7
M Writer für unterschiedliche Obj/inbt/double erstellen? Java Basics - Anfänger-Themen 1
F Character umwandeln als Double Werte Java Basics - Anfänger-Themen 8
M Double Wert nach n abschneiden ohne zu runden Java Basics - Anfänger-Themen 1
D Methode mit Übergabe double und Rückgabe String Java Basics - Anfänger-Themen 2
P Hilfe bei Double Java Basics - Anfänger-Themen 1
B Rückgabe von zwei Werten: String und double Java Basics - Anfänger-Themen 14
B HQL / Hibernate, GroupBy und Ausgabe als Double Java Basics - Anfänger-Themen 1
M Konvertierung String -> double Java Basics - Anfänger-Themen 8
A Double Scan eingrenzen Java Basics - Anfänger-Themen 2
O Erste Schritte Potenzmethode per double Java Basics - Anfänger-Themen 11
A Random Double mit Math.round() runden? Java Basics - Anfänger-Themen 1
H Double oder nicht? Java Basics - Anfänger-Themen 7
J int array als double array ausgeben Java Basics - Anfänger-Themen 9
M Int und Double in Array speichern Java Basics - Anfänger-Themen 1
J String, Int und double Array sortieren Java Basics - Anfänger-Themen 16
B Hashing (verkettet/double) Java Basics - Anfänger-Themen 0
L Konvertieren von String zu double?! Java Basics - Anfänger-Themen 6
V Operatoren Warum kommt bei double bei den Nachkommastellen irgendwann eine 2?! (1.20000000000002) Java Basics - Anfänger-Themen 5
geekex Double zu String umwandeln in einer Methode Java Basics - Anfänger-Themen 28
E Bruch erstellen - Von Int zu Double Ergebnis Java Basics - Anfänger-Themen 24
G Probleme beim casten von double zu int Java Basics - Anfänger-Themen 3
I Double.ParseDouble 2 Textfelder Java Basics - Anfänger-Themen 1
M JComboBox feste double Werte zu ordnen Java Basics - Anfänger-Themen 8
P Datentypen Kann ich bei double Komma statt Punkt eingeben? Java Basics - Anfänger-Themen 14
E Von Double zu Long umwandeln Java Basics - Anfänger-Themen 9
L Bei falscher Eingabe soll NaN zurückgegeben werden, Rückgabetyp jedoch double Java Basics - Anfänger-Themen 3
V Variablen Double später deklarieren Java Basics - Anfänger-Themen 7
V double = 1.34823e-300 Java Basics - Anfänger-Themen 5
W double*double error Java Basics - Anfänger-Themen 4
kilopack15 Mehr Nachkommastellen mit double Java Basics - Anfänger-Themen 14
T Input/Output Double und String als Eingabe einlesen Java Basics - Anfänger-Themen 9
J [Rundungsfehler bei Double] Grundkurs Java: Checke Lösungsweg nicht Java Basics - Anfänger-Themen 1
W In einer Function<Double, Double> undefinierte Rechenoperationen abfangen? Java Basics - Anfänger-Themen 3
T set Metode für Double Java Basics - Anfänger-Themen 6
Hijo2006 String to Double Java Basics - Anfänger-Themen 4
K Double Wert runden und in Int umwandeln Java Basics - Anfänger-Themen 7
A Kommafehler beim double einleseen korrigieren Java Basics - Anfänger-Themen 2
K Operatoren The Operator * is undefined for the argument type(s) double, String Java Basics - Anfänger-Themen 4
das_leon String zu double konventieren Java Basics - Anfänger-Themen 1
K Genauer als Double? Java Basics - Anfänger-Themen 4
T Double.parseDouble(args[0]) Java Basics - Anfänger-Themen 13
A Java Ungenauigkeit double Java Basics - Anfänger-Themen 6
B Methoden The method mirror(double[]) in the type Convolution is not applicable for the arguments (double) Java Basics - Anfänger-Themen 8
C Typumwandlung von int<-->double Java Basics - Anfänger-Themen 6
M Double Wert auf 2 Kommastellen runden Java Basics - Anfänger-Themen 2
S Regelabfragen aus Double-Array Java Basics - Anfänger-Themen 2
A Erste Schritte Double Wert aus String zu int Java Basics - Anfänger-Themen 2
P Rückgabe erflogt nicht als Double Java Basics - Anfänger-Themen 2
K Erste Schritte switch - Warum sind long/float/double/... nicht erlaubt? Java Basics - Anfänger-Themen 5
P scanner ein Double einlesen Java Basics - Anfänger-Themen 10
T Java double berechnung fehler Java Basics - Anfänger-Themen 2
S double[x] , double[y] zu Point[] points kopieren? Java Basics - Anfänger-Themen 15
G double in float umwandeln Java Basics - Anfänger-Themen 2
F double[] an andere Methode übergeben Java Basics - Anfänger-Themen 1
B Datentypen Test float und double speichern Zahlen nur ungefähr Java Basics - Anfänger-Themen 4
S Datentypen double - kommastellen abschneiden Java Basics - Anfänger-Themen 6
M int double int double Graph Java Basics - Anfänger-Themen 3
K ArrayList<Double> --> double[] array Java Basics - Anfänger-Themen 5
Z Double in komma und Punkt akzeptieren -> Robusteeingabe Java Basics - Anfänger-Themen 7
S Double und Gleitkommazahlen mit JUnit testen Java Basics - Anfänger-Themen 7
K Von einem Double wert nur die Zahl vor dem Komma verwenden Java Basics - Anfänger-Themen 9
F Double neu formatieren mit NumberFormat Java Basics - Anfänger-Themen 2
M Double-Ausgabe in JTextField fehlerhaft Java Basics - Anfänger-Themen 2
T Problem mit double-Formatierung Java Basics - Anfänger-Themen 3
M Double Zahl in Grad Zahl Java Basics - Anfänger-Themen 7
M Datentypen Ergebniss- Double to String- wird nicht angezeigt Java Basics - Anfänger-Themen 13
S Double mithilfe eines Scanners so einlesen, dass ich damit rechnen kann Java Basics - Anfänger-Themen 4
M Die Double-Variable rundet? Java Basics - Anfänger-Themen 1
llabusch Methoden Methoden überlagern - entweder int || double Java Basics - Anfänger-Themen 10
S Double, int, Berechnung Java Basics - Anfänger-Themen 3
K Datentypen Wertebereich float/double - Warum nicht hoch -1 Java Basics - Anfänger-Themen 6
A Double[] Array zahlen per Argument übergeben Java Basics - Anfänger-Themen 5
B Erste Schritte Addition von double in switch-Anweisung Java Basics - Anfänger-Themen 2
D Unterschied zwischen double und Double Java Basics - Anfänger-Themen 4
M Double-Zahlen auf Intervalle runden Java Basics - Anfänger-Themen 3
D Schon wieder double -.- Java Basics - Anfänger-Themen 4

Ähnliche Java Themen

Neue Themen


Oben