2015-04-17 11 views
8

Was gibt sys.float_info.epsilon zurück?Python Epsilon ist nicht die kleinste Zahl

Auf meinem System erhalte ich:

>>> sys.float_info.epsilon 
2.220446049250313e-16 
>>> sys.float_info.epsilon/2 
1.1102230246251565e-16 
>>> 0 < sys.float_info.epsilon/2 < sys.float_info.epsilon 
True 

Wie ist das möglich?

EDIT:

Alles in Ordnung sind, dachte ich epsilon tut, was min tut. Also meinte ich eigentlich sys.float_info.min.

EDIT2

Jeder und vor allem John Kugelman, vielen Dank für Ihre Antworten!

Einige Spiel um Ich habe Dinge zu mir selbst zu klären:

>>> float.hex(sys.float_info.epsilon) 
'0x1.0000000000000p-52' 
>>> float.hex(sys.float_info.min) 
'0x1.0000000000000p-1022' 
>>> float.hex(1 + a) 
'0x1.0000000000001p+0' 
>>> float.fromhex('0x0.0000000000001p+0') == sys.float_info.epsilon 
True 
>>> float.hex(sys.float_info.epsilon * sys.float_info.min) 
'0x0.0000000000001p-1022' 

So gibt epsilon * min die Zahl mit der kleinsten positiven Signifikanden (oder Mantisse) und dem kleinsten Exponenten.

Antwort

3

epsilon ist der Unterschied zwischen 1 und dem nächsten darstellbaren Float. Das ist nicht das Gleiche wie der kleinste Schwimmer, der 0, nicht 1 ist.

Es gibt zwei kleinste Schwimmer, abhängig von Ihren Kriterien. min ist der kleinste normalized float. Der kleinste subnormal Float ist min * epsilon.

>>> sys.float_info.min 
2.2250738585072014e-308 
>>> sys.float_info.min * sys.float_info.epsilon 
5e-324 

Beachten Sie die Unterscheidung zwischen normalisierten und subnormale Schwimmern: min ist eigentlich nicht der kleinste Schwimmer, es ist nur der kleinste mit voller Genauigkeit. Subnormale Zahlen decken den Bereich zwischen 0 und min ab, aber sie verlieren viel Präzision. Beachten Sie, dass 5e-324 nur eine signifikante Ziffer hat. Mit Subnomen arbeiten Sie auch viel langsamer, bis zu 100x langsamer als normalisierte Floats.

>>> (sys.float_info.min * sys.float_info.epsilon)/2 
0.0 
>>> 4e-324 
5e-324 
>>> 5e-325 
0.0 

Diese Tests bestätigen, dass 5e-324 wirklich der kleinste Schwimmer ist. Die Division durch zwei Unterschreitungen auf 0

Siehe auch: What is the range of values a float can have in Python?

+0

Mein Beispiel funktioniert auf die gleiche Weise für sys.float_info.min anstelle von sys.float_info.epsilon überall. Wie erklärst du das? –

+0

Alles, was kleiner ist als "min" ist subnormal. 'min * epsilon' ist der wahre kleinste Float. Wenn Sie es durch 2 teilen, wird es auf 0 unterschritten. –

0

Ihr letzter Ausdruck ist möglich, denn für jede echte, positive Zahl, 0 < num/2 < num.

Von the docs:

Differenz zwischen 1 und dem geringstenen Wert größer als 1, der als Schwimmer

0

sys.float_info als

Unterschied zwischen 1 darstellbaren ist definiert und der kleinste Wert größer als 1 ist darstellbar als ein Gleitkomma

auf this page.

1

Sie wollen eigentlich sys.float_info.min ("Minimum positive normalisierte float"), die auf der Maschine gibt mir .2250738585072014e-308.

epsilon ist:

Differenz zwischen 1 und dem kleinsten Wert größer als 1, der als Schwimmer

Siehe docs für weitere Informationen auf den Gebieten der sys.float_info darstellbare ist.

+0

'min' ist immer noch nicht ganz der kleinste positive float; Es sind immer noch Unternormale darunter. – user2357112

+0

Danke, Sie haben Recht, aber wie erklären Sie, was @ user2357112 gesagt hat? –

+1

Subnormale Floats bedeuten, dass die Zahl in ihrem Signifikanten Nullen hat; Ich denke @ John Kugelman hat an dieser Stelle die bessere Antwort: Ich würde das akzeptieren, wenn es für dich funktioniert, ansonsten kann ich dieses Update aktualisieren, wenn es nicht funktioniert. – Isaac

0

Die documentation definiert sys.float_info.epsilon als

Differenz zwischen 1 und dem geringsten Wert größer als 1, der als Schwimmer

jedoch darstellbare ist, ist der Zwischenraum zwischen aufeinanderfolgenden Hin- und Herbewegungen für größere floats größeren , so ist die Lücke zwischen epsilon und dem nächsten kleineren Schwimmer viel kleiner als epsilon. Insbesondere ist der nächst kleinere Float nicht 0.

0

Wie jede Antwort sagt, es ist der Unterschied zwischen 1 und dem nächsten größten Wert, der dargestellt werden kann, wenn man die Hälfte davon 1 hinzuzufügen versucht, Sie erhalten 1 zurück

>>> (1 + (sys.float_info.epsilon/2)) == 1 
True 

Zusätzlich, wenn Sie versuchen, 1 zwei Drittel davon hinzuzufügen, können Sie den gleichen Wert erhalten werden:

>>> (1 + sys.float_info.epsilon) == (1 + (sys.float_info.epsilon * (2./3))) 
True 
Verwandte Themen