Erklärung der Gleitkommazahlen

Ursprünglicher Autor: Fabien Sanglard
  • Übersetzung
Bild

In den frühen 90er Jahren bedeutete die Schaffung einer dreidimensionalen Spiel-Engine, dass Sie die Maschine zwingen mussten, Aufgaben auszuführen, die für sie fast nicht charakteristisch waren. Personal Computer dieser Zeit wurden entwickelt, um Textverarbeitungs- und Tabellenkalkulationsprogramme auszuführen, und nicht für 3D-Computer mit einer Frequenz von 70 Bildern pro Sekunde. Ein schwerwiegendes Hindernis war, dass die CPU trotz ihrer Leistungsfähigkeit kein Hardware-Gerät für Gleitkommaberechnungen hatte. Programmierer hatten nur ALU-Schleif-Ganzzahlen.

Als ich ein Game Engine Black Book: Wolfenstein 3D- Buch schrieb, wollte ich zeigen, wie groß die Probleme waren, wenn ich ohne Fließkomma arbeitete. Meine Versuche, Gleitkommazahlen mit kanonischen Artikeln herauszufindendas Gehirn mit Feindseligkeit wahrgenommen. Ich fing an, nach einem anderen Weg zu suchen. Irgendwas weit weg von$ (- 1) ^ S * 1.M * 2 ^ {(E-127)} $und ihre kryptischen Exponenten mit Mantissen. Vielleicht in Form einer Zeichnung, weil mein Gehirn sie einfacher wahrnimmt.

Aus diesem Grund habe ich diesen Artikel geschrieben und beschlossen, ihn dem Buch hinzuzufügen. Ich werde nicht behaupten, dass dies meine Erfindung ist, aber bisher habe ich keine solche Erklärung für Gleitkommazahlen gesehen. Ich hoffe, dieser Artikel hilft denen, die wie ich allergisch gegen mathematische Notationen sind.

Als Gleitkommazahlen werden in der Regel erklärt


Ich zitiere David Goldbert:

Für viele Menschen scheint Fließkomma-Arithmetik eine Art Geheimwissen zu sein.

Ich stimme ihm vollkommen zu. Es ist jedoch wichtig, die Prinzipien seiner Arbeit zu verstehen, um seine Nützlichkeit bei der Programmierung einer 3D-Engine voll auszuschöpfen. In C sind Gleitkommawerte 32-Bit-Container, die der IEEE 754-Norm entsprechen. Sie dienen zum Speichern und Ausführen von Operationen mit Approximationen von reellen Zahlen. Bisher habe ich nur eine solche Erklärung von ihnen gesehen. 32 Bits sind in drei Teile unterteilt:

  • S (1 Bit) zur Zeichenspeicherung
  • E (8 Bit) für Exponent
  • M (23 Bits) für die Mantisse


Das Innere von Gleitkommazahlen.


Drei Teile einer Gleitkommazahl.

So weit, so gut. Lass uns weitermachen. Die Methode zur Interpretation von Zahlen wird normalerweise mit der folgenden Formel erklärt:

$ (- 1) ^ S * 1, M * 2 ^ {(E-127)} $


Es ist diese Erklärung von Gleitkommazahlen, die jeder hasst.

Und hier fange ich normalerweise an, die Geduld zu verlieren. Ich bin möglicherweise allergisch gegen mathematische Notationen, aber wenn ich sie lese, klickt nichts in meinem Gehirn. Diese Erklärung ähnelt der Art und Weise, wie eine Eule gezeichnet wird:



Eine andere Art zu erklären


Obwohl dies zutrifft, gibt uns diese Art der Erklärung von Gleitkommazahlen normalerweise kein Verständnis. Ich beschuldige diese schreckliche Bilanz, Tausende von Programmierern enttäuscht zu haben und sie so erschreckt zu haben, dass sie nie wieder versucht haben, herauszufinden, wie Gleitkommaberechnungen tatsächlich funktionieren. Glücklicherweise können sie unterschiedlich erklärt werden. Stellen Sie sich den Exponenten als Fenster oder als Intervall zwischen zwei benachbarten ganzzahligen Zweierpotenzen vor. Stellen Sie sich Mantisse in diesem Fenster als Versatz (Offset) vor.


Drei Teile einer Gleitkommazahl.

Das Fenster sagt uns, zwischen welchen zwei aufeinanderfolgenden Zweierpotenzen sich eine Zahl befinden wird: [0,1], [1,2], [2,4], [4,8] und so weiter (bis zu [$ 2 ^ {127} $,$ 2 ^ {128} $]. Der Versatz teilt das Fenster in$ 2 ^ {23} = 8388608 $Segmente. Mit dem Fenster und dem Versatz können Sie die Anzahl approximieren. Ein Fenster ist ein hervorragender Schutz vor Grenzüberschreitungen. Wenn Sie im Fenster das Maximum erreicht haben (z. B. in [2,4]), können Sie nach rechts "schwimmen" und die Zahl im nächsten Fenster anzeigen (z. B. [4,8]). Der Preis dafür wird nur eine geringfügige Verringerung der Genauigkeit sein, da das Fenster doppelt so groß wird.

Quiz: Wie viel Genauigkeit geht verloren, wenn ein Fenster ein größeres Intervall schließt? Nehmen wir ein Beispiel mit dem Fenster [0,1], in dem 8388608 Offsets einem Intervall der Größe 1 überlagert sind, was uns Genauigkeit gibt$ \ frac {(1-0)} {8388608} = $ 0.00000011920929. Im Fenster [2048.4096] überlappen 8388608 Offsets das Intervall$ (4096-2048) = $ 2048das gibt uns Genauigkeit $ \ frac {(4096-2048)} {8388608} = $ 0,0002.

Die folgende Abbildung zeigt, wie die Nummer 6.1 codiert ist. Das Fenster sollte mit 4 beginnen und mit der nächsten Zweierpotenz enden, d.h. 8. Der Versatz liegt ungefähr in der Mitte des Fensters.


Ein Wert von 6.1, der durch eine Gleitkommazahl approximiert wird.

Nehmen wir ein weiteres Beispiel mit einer detaillierten Berechnung, indem wir einen uns allen bekannten Wert als Gleitkommazahl darstellen: 3.14.

  • Die Zahl 3.14 ist positiv $ \ rightarrow S = 0 $.
  • Die Zahl 3.14 liegt zwischen den Zweierpotenzen 2 und 4, dh das Gleitkommazahlenfenster sollte mit beginnen $ 2 ^ 1 $$ \ rightarrow E = 128 $ (Siehe die Formel, in der sich das Fenster befindet $ 2 ^ {(E-127)} $)
  • Endlich da $ 2 ^ {23} $Verschiebungen, durch die die Position von 3.14 innerhalb des Intervalls ausgedrückt werden kann [2-4]. Es befindet sich in$ \ frac {3,14 -2} {4 - 2} = $ 0,57 innerhalb des Intervalls, das uns den Offset gibt $ M = 2 ^ {23} * 0,57 = $ 4,781,507

In binärer Form bedeutet dies Folgendes:

  • S = 0 = 0b
  • E = 128 = 10000000b
  • M = 4781507 = 10010001111010111000011b


Die binäre Darstellung der Gleitkommazahl ist 3.14.

Das heißt, der Wert von 3,14 wird als 3,1400001049041748046875 angenähert.

Der entsprechende Wert in einer unverständlichen Formel:

$ 3.14 = (-1) ^ 0 * 1.57 * 2 ^ {(128-127)} $


Und schließlich eine grafische Darstellung mit einem Fenster und einem Versatz:


Fenster- und Zahlenversatz 3.14.

Interessant: Wenn die Operation Module Schwimmer waren so langsam, warum die Sprache C als Folge der Verwendung der Typen float und double ? Tatsächlich gab es in der Maschine, auf der die Sprache erfunden wurde (PDP-11), kein Modul für Gleitkommaoperationen! Tatsache ist, dass der Hersteller (DEC) Dennis Ritchie und Ken Thompson versprochen hat, dass er im nächsten Modell sein wird. Sie waren Astronomieliebhaber und beschlossen, diese beiden Typen in die Sprache aufzunehmen.

Interessante Tatsache:Wer 1991 wirklich ein Fließkomma-Hardwaremodul brauchte, konnte es kaufen. Die einzigen Leute, die es zu dieser Zeit brauchen könnten, waren Wissenschaftler (zumindest hat Intel die Bedürfnisse des Marktes verstanden). Im Markt positionierten sie sich als „mathematische Coprozessoren“. Ihre Leistung war durchschnittlich und der Preis ist riesig (200 US-Dollar im Jahr 1993 - das sind 350 US-Dollar im Jahr 2016). Infolgedessen war das Umsatzniveau mittelmäßig.



Ich hoffe, der Artikel hat Ihnen weitergeholfen!

Jetzt auch beliebt: