Ein Angebot von

Vergleich von Gleitkommazahlen – knifflig, aber machbar!

| Autor / Redakteur: Matt Kline * / Sebastian Gerstl

Layout eines 64-Bit IEEE 754 Floats.
Layout eines 64-Bit IEEE 754 Floats. (Bild: IEEE 754 Double Floating Point Format / Codekaizen IEEE 754 Double Floating Point Format / Codekaizen / CC BY-SA 4.0 / CC BY-SA 4.0)

Gleitkomma-Mathematik ist mit recht diffizilen und subtilen Problemen belastet. Der Vergleich von Werten macht da keine Ausnahme. In diesem Artikel diskutieren wir häufige Fallstricke, untersuchen mögliche Lösungen und versuchen, „Boost“-Probleme zu überlisten.

Wenn Sie eine nicht ganzzahlige Zahl in einer der etablierten Programmiersprachen darstellen wollen, werden Sie letzten Endes wahrscheinlich Gleitkomma-Zahlen nach IEEE 754 verwenden. Nach ihrer Normung 1984 wurden sie einfach allgegenwärtig. Fast alle modernen CPUs – und viele Mikroprozessoren – haben für sie eine spezielle Hardware, die sogenannten Floating-Point Units (FPUs, Gleitkomma-Einheiten).

Jede Variable des Typs float besteht aus einem Vorzeichenbit, einigen Bits, die den Exponenten repräsentieren und Bits, die einen Bruchteil, auch Mantisse genannt, darstellen. In den meisten Fällen kann der Wert einer Gleitkomma-Zahl durch diese Gleichung dargestellt werden.

Formel 1: Wert einer Gleitkomma-Zahl.
Formel 1: Wert einer Gleitkomma-Zahl. (Bild: Matt Kline / Bitbashing.io)

Hierbei stellt s unser Vorzeichenbit dar, m einen Bruchteil, der durch die Bits der Mantisse repräsentiert wird, e eine vorzeichenlose Ganzzahl, die durch die Bits des Exponenten dargestellt wird und c ist der halbe Maximalwert von e, das heißt 127 für eine 32-Bit Gleitkomma-Zahl und 1023 für eine 64-Bit Gleitkomma-Zahl.

Formel 2: Abwandlung der Gleichung, sobald alle Bits des Exponenten gleich Null betragen.
Formel 2: Abwandlung der Gleichung, sobald alle Bits des Exponenten gleich Null betragen. (Bild: Matt Kline / bitbashing.io)

Es gibt aber auch einige Spezialfälle. Sind zum Beispiel alle Bits des Exponenten Null, ändert sich die Formel entsprechend. Bemerkenswert ist der Entfall der „1“ vor der Mantisse. Dies erlaubt es uns, kleine Werte nahe Null zu speichern, sogenannte normalisierte oder denormalisierte Werte. Und wenn alle Bits im Exponenten Einsen sind, repräsentieren bestimme Werte der Mantisse +∞, - ∞ und keine Zahl (NaN / Not a Number), das Ergebnis einer undefinierten oder nicht darstellbaren Rechenoperation wie die Division durch Null.

Hier sind zwei Beobachtungen festzuhalten, die sich in Kürze als nützlich herausstellen.

1. Variablen vom Typ float können keine beliebigen realen Zahlen speichern, ganz zu schweigen von beliebigen rationalen Zahlen. Sie können ausschließlich Zahlen speichern, die durch die oben gezeigten Gleichungen dargestellt werden können. Wenn ich zum Beispiel die folgende Variable deklariere:

float f = 0.1f;

wird f als 0.100000001490116119384765625 dargestellt, was dem an 0,1 nächstliegenden 32-Bit Gleitkomma-Wert entspricht.

2. Da die Gleichungen exponentiell sind, nimmt der Abstand auf der Zahlengerade zwischen benachbarten Werten zu – und zwar exponentiell, je weiter man sich von der Null entfernt. Der Abstand zwischen 1,0 und dem nächsten möglichen Wert ist ungefähr 1,19 x 10-7, aber der Abstand zwischen zwei benachbarten Gleitkomma-Zahlen in der Nähe von 6,022 x 1023 ist ungefähr 3,6 x 1016. Das wird sich als eine unserer größten Herausforderung herausstellen: Wenn wir Gleitkomma-Zahlen vergleichen wollen, dann wollen wir Eingaben in der Nähe von Null genauso handhaben, wie Zahlen in der Nähe der Avogadro-Konstante.

Inhalt des Artikels:

Kommentar zu diesem Artikel abgeben

Schreiben Sie uns hier Ihre Meinung ...
(nicht registrierter User)

Zur Wahrung unserer Interessen speichern wir zusätzlich zu den o.g. Informationen die IP-Adresse. Dies dient ausschließlich dem Zweck, dass Sie als Urheber des Kommentars identifiziert werden können. Rechtliche Grundlage ist die Wahrung berechtigter Interessen gem. Art 6 Abs 1 lit. f) DSGVO.
Kommentar abschicken
copyright

Dieser Beitrag ist urheberrechtlich geschützt. Sie wollen ihn für Ihre Zwecke verwenden? Infos finden Sie unter www.mycontentfactory.de (ID: 44970621 / Implementierung)