2010-07-22 8 views
10

entspricht log10 (2^24) ≈ 7.225 DezimalziffernDezimalgenauigkeit von Schwimmern

Wikipedia

Präzision: 7 Ziffern

MSDN

std::numeric_limits<float>::digits10 

Warum numeric_limits zurückkehren hier 6? Sowohl Wikipedia als auch MSDN berichten, dass Gleitkommazahlen eine Genauigkeit von 7 Dezimalstellen haben.

+1

Ich denke du meintest std :: numeric_limits :: digits10, richtig? – Scharron

+0

@Scharron: Richtig, danke, dass du das gesehen hast. Fehler beim Kopieren und Einfügen – liori

+0

mögliches Duplikat von [Ist die höchstwertige Dezimalziffer die Genauigkeit, die ohne Signifikanzverlust in 6 oder 7,225 in binär und zurück in Dezimal konvertiert werden kann?] (Http://stackoverflow.com/questions/30688422/is-the-most-) signifikante Dezimalstellen-Genauigkeit-die-in-binär konvertiert werden kann – Bryan

Antwort

13

Im Zweifelsfall ist die Spezifikation zu lesen. Der C++ Standard besagt, dass digits10 ist:

Anzahl der Basis 10 Ziffern, die ohne Änderung dargestellt werden können.

Das ist ein wenig vage; Glücklicherweise gibt es eine Fußnote:

Entspricht FLT_DIG, DBL_DIG, LDBL_DIG

Diese werden im C-Standard definiert sind; Lassen Sie uns es dort nachschauen:

Anzahl der Dezimalstellen, q, so dass jeder Gleitkommazahl mit q Dezimalstellen in eine Fließkommazahl gerundet werden kann mit p radix b Ziffern und wieder zurück ohne Änderung die q Dezimalziffern.

So ist std::numeric_limits<float>::digits10 die Anzahl der Dezimalstellen, so dass jeder Gleitkommazahl mit so vielen Stellen ist unverändert, wenn Sie es zu einem float und zurück konvertieren in Dezimalzahlen.

Wie Sie sagen, den Schwimmer hat etwa 7 Stellen der Dezimalgenauigkeit, aber die Fehler in Vertretung beiden feste Breite Dezimalzahlen und schwimmt nicht gleichmäßig logarithmisch. Der relative Fehler eine Zahl der Form 1.xxx .. auf eine feste Anzahl von Dezimalstellen gerundet ist nahezu zehnmal größer ist als die relativen Fehler von 9.xxx Rundung .. auf die gleiche Anzahl von Dezimalstellen. Auf ähnliche Weise, je nachdem wo ein Wert fiel in einem Binade, der relative Fehler es bis zu 24 Binärstellen in Abrunden kann um einen Faktor von nahezu zwei variieren.

Das Ergebnis davon ist, dass nicht alle siebenstelligen Dezimalzahlen die Rundreise überleben zu schweben und zurück, aber alle sechsstelligen Dezimalzahlen tun. Daher ist std::numeric_limits<float>::digits10 6.

Es gibt nicht so viele sechs- und siebenstellige Dezimalstellen mit Exponenten in einem gültigen Bereich für den Typ float; Sie können ziemlich leicht ein Programm schreiben, um alle von ihnen erschöpfend zu prüfen, wenn Sie noch nicht überzeugt sind.

+0

reg. "Aber alle sechsstelligen Dezimalstellen machen" was ist mit 0,3 (dezimal)? Kannst du bitte mehr auf diese Art von Zahlen eingehen? –

+1

0,3 in float umgewandelt (unter Annahme von IEEE-754 single-precision hier) ist genau "0.300000011920928955078125". Wenn dieser Wert auf sechs Dezimalstellen gerundet wird, ist das Ergebnis 0,3, so dass es unverändert bleibt, wenn es mit sechs Stellen float und zurück zu dezimal ist. Dies gilt für alle sechsstelligen Dezimalstellen im darstellbaren Bereich von float. –

+0

Mit Dezimalstellen mit fester Breite meinen Sie [Festpunktzahlen] (http://en.wikipedia.org/wiki/Q_%28number_format%29) oder ganzzahlige Typen? – legends2k

2

Es ist wirklich nur 23 Bits in der Mantisse (es gibt eine implizite 1, so dass er 24 ist effektiv Bits, aber die 1 variiert natürlich nicht). Dies gibt 6,923689900271567 Dezimalstellen Präzision, die nicht ganz 7.

+0

Nicht offensichtlich. Alle normalisierten Zahlen haben das implizierte 1. Aber dein Kommentar erinnerte mich an denormalisierte Zahlen, die weniger Präzisionsbits haben. Vielen Dank. – liori

Verwandte Themen