HOWTO · C
Zahlen in wissenschaftlicher Notation in C drucken
Dieser Artikel beschreibt das Drucken von Zahlen in wissenschaftlicher Notation in C.
Auf dieser Seite
Verwenden Sie in printf die Konvertierung %e oder %E, um einen Gleitkommawert in wissenschaftlicher Notation auszugeben. Die kleingeschriebene Konvertierung gibt ein kleines Exponentenkennzeichen aus, die großgeschriebene ein großes. Mit einer Genauigkeit wie %.3e legen Sie fest, wie viele Ziffern nach dem Dezimalpunkt der Mantisse ausgegeben werden.
Führen Sie dieses Beispiel aus:
Der Code und die angezeigten Bezeichnungen oder Ausgaben in diesem Abschnitt bleiben auf Englisch.
#include <stdio.h>
int main(void) {
double values[] = {123456.789, -0.000012345};
printf("lowercase: %.3e\n", values[0]);
printf("uppercase: %.3E\n", values[1]);
return 0;
}
So funktioniert wissenschaftliche Notation in C
Bei der wissenschaftlichen Notation wird ein Wert ungleich null als Mantisse multipliziert mit einer Zehnerpotenz geschrieben. Die Mantisse hat genau eine von null verschiedene Ziffer vor dem Dezimalpunkt; der Exponent gibt an, um wie viele Stellen das Dezimalzeichen verschoben wird. Zum Beispiel lässt sich 123456 als 1.23456 × 10^5 schreiben und 0.0000123 als 1.23 × 10^-5.
Diese Notation verändert die Darstellung eines Werts, nicht die Art, wie der zugrunde liegende float- oder double-Typ ihn speichert. Binäre Gleitkommatypen haben eine begrenzte Genauigkeit, daher sind viele Dezimalbrüche im Speicher Näherungswerte. Bei der Ausgabe weiterer Ziffern wird möglicherweise mehr von diesem gespeicherten Näherungswert sichtbar; der gespeicherte Wert wird dadurch nicht genauer.
Wissenschaftliche Notation mit printf ausgeben
Die Konvertierungen e und E formatieren ein double-Argument in wissenschaftlicher Notation. Die Groß- oder Kleinschreibung des Exponentenkennzeichens richtet sich nach der Konvertierung: %e verwendet e, %E verwendet E. Der Exponent enthält ein Vorzeichen, und die Implementierungen geben genügend Ziffern aus, um ihn darzustellen. Wenn Sie zum Vergleich eine Festkommadarstellung wünschen, verwenden Sie %f. Die POSIX-Spezifikation für fprintf legt die Konvertierungen e und E sowie deren Genauigkeitsverhalten fest.
Im einleitenden Beispiel geben %.3e und %.3E jeweils drei Ziffern nach dem Dezimalpunkt der Mantisse aus. Das Vorzeichen des Werts bleibt Teil der formatierten Zahl. Bei Werten, deren Festkommaausgabe schwer lesbar wäre, hält die wissenschaftliche Notation die Mantisse kompakt; der Exponent gibt die Größenordnung an.
Die Konvertierung erwartet ein double-Argument. Ein an printf übergebener float wird zu double hochgestuft, eine Ganzzahl dagegen nicht. Um einen ganzzahligen Wert wissenschaftlich zu formatieren, wandeln Sie ihn explizit um, zum Beispiel mit (double)count, und verwenden Sie %e oder %E. Bei der Umwandlung großer Ganzzahlen können niederwertige Ziffern verloren gehen, wenn der Wert die Genauigkeit überschreitet, die double darstellen kann.
Anzahl der Ziffern nach dem Dezimalpunkt festlegen
Bei %e und %E zählt die Genauigkeit die Ziffern nach dem Dezimalpunkt, nicht die Gesamtzahl der signifikanten Ziffern. %.2e gibt daher zwei Nachkommastellen der Mantisse aus, insgesamt meist also drei signifikante Ziffern. Wenn Sie keine Genauigkeit angeben, beträgt der Standardwert sechs Ziffern nach dem Dezimalpunkt. Für die Ausgabe wird der Wert auf die angegebene Genauigkeit gerundet; der gespeicherte Wert bleibt unverändert. Die POSIX-Spezifikation für fprintf beschreibt die Genauigkeitsregel und den Standardwert von sechs Ziffern.
Wählen Sie die Genauigkeit passend zur gewünschten Anzeige oder zum Austauschformat Ihrer Anwendung. Eine größere Zahl ausgegebener Ziffern garantiert nicht, dass die Dezimalzeichenfolge den binären Gleitkommawert exakt darstellt. Wenn Sie eine bestimmte Anzahl signifikanter Ziffern benötigen, berücksichtigen Sie bei der Wahl der Genauigkeit die führende Ziffer der Mantisse.
Zeichenfolgen mit wissenschaftlicher Notation sicher formatieren
Wenn die formatierte Zahl gespeichert oder an eine andere Funktion übergeben werden soll, verwenden Sie snprintf mit einer Puffergröße. Diese Größe schließt das abschließende Nullzeichen ein. Die Funktion gibt die Anzahl der Zeichen zurück, die geschrieben worden wären, ohne dieses Nullzeichen mitzuzählen. Ein Rückgabewert, der größer oder gleich der Puffergröße ist, bedeutet, dass die Ausgabe abgeschnitten wurde. Ein negativer Rückgabewert weist auf einen Formatierungsfehler hin. Die POSIX-Spezifikation für fprintf beschreibt den Rückgabewert und das Abschneideverhalten von snprintf.
Führen Sie dieses eigenständige Beispiel aus:
Der Code und die angezeigten Bezeichnungen oder Ausgaben in diesem Abschnitt bleiben auf Englisch.
#include <stdio.h>
int main(void) {
double measurement = 0.000012345;
char text[64];
int length = snprintf(text, sizeof text, "%.3e", measurement);
if (length < 0) {
puts("formatting error");
return 1;
}
if ((size_t)length >= sizeof text) {
puts("buffer too small");
return 1;
}
printf("value: %s\n", text);
return 0;
}
snprintf schreibt höchstens so viele Zeichen, wie in die verfügbare Puffergröße passen, und terminiert den Puffer, wenn seine Größe größer als null ist. Prüfen Sie den Rückgabewert, bevor Sie den Puffer als vollständiges formatiertes Ergebnis verwenden. Vermeiden Sie ein unbegrenztes sprintf, wenn nicht sichergestellt ist, dass der Puffer groß genug ist.
Sollten Sie eine eigene Funktion für wissenschaftliche Notation schreiben?
In der Regel nicht. %e und %E behandeln Mantisse, Exponent, Vorzeichen, Rundung und den Wert null bereits gemäß den Formatierungsregeln der C-Bibliothek. Eine selbst geschriebene Konvertierung muss null gesondert behandeln und Werte kleiner als eins ebenso normalisieren wie Werte ab zehn. Außerdem muss sie negative Werte, Rundungen, durch die sich die Mantisse ändert, und die Grenzen des Zahlentyps berücksichtigen. Eine Schleife, die nur positive Werte wiederholt durch zehn teilt, deckt diese Fälle nicht korrekt ab.
Verwenden Sie printf für die direkte Ausgabe und snprintf für die Formatierung in eine begrenzte Zeichenfolge. Schreiben Sie nur dann einen eigenen Formatierer, wenn Sie eine bestimmte Darstellung benötigen, die die Standardkonvertierungen nicht bieten, und legen Sie sein Verhalten für den gesamten Eingabebereich fest und prüfen Sie es. Für gewöhnliche wissenschaftliche Notation sind die Standardkonvertierungen kürzer und weniger fehleranfällig.