2009-06-24 13 views
1

Problem:, um zu sehen, wenn der Computer Annäherung in mathematischen Berechnungen macht, wenn ich Python verwendenkann nicht Pythons Annäherungen in mathematischen Berechnungen, um zu sehen

Beispiel des Problems:

Mein alter Lehrer sagte einmal die folgend Aussage

You cannot never calculate 200! with your computer. 

Ich bin nicht ganz sicher, ob es wahr ist oder nicht heutzutage. Es scheint, dass es ist, seit ich eine Menge Nullen dafür von einem Python script bekomme.

Wie können Sie sehen, wenn Ihr Python-Code Annäherungen macht?

+2

Es ist nicht sehr schwer 200 zu berechnen! heutzutage. Siehe http://www53.wolframalpha.com/input/?i=200! –

+0

Beachten Sie, dass die obige URL das "!" Charakter. Ich bin mir nicht sicher, warum SO es nicht als Teil des Links enthält. –

+0

Beim automatischen Verknüpfen von Text zum Ignorieren von Satzzeichen (außer Schrägstrich) am Ende einer URL ist es im Allgemeinen eine gute Übung. In 99% der Fälle hat der Benutzer eine nicht interpunktierte URL in Klammern oder in einem Satz eingefügt, und das Einfügen der Interpunktion würde den Link unterbrechen. Sie hatten gerade das Pech, eines der verbleibenden 1% der Fälle zu sein. –

Antwort

7

Python Verwendung arbitrary-precision arithmetic mit Ganzzahlen zu berechnen, so kann es genau berechnen 200!. Für reelle Zahlen (so genannte floating-point) verwendet Python keine exakte Repräsentation. Es verwendet eine binäre Darstellung namens IEEE 754, die im Wesentlichen wissenschaftliche Notation ist, mit Ausnahme von Base 2 anstelle von Base 10.

So jede echte Zahl, die nicht genau in der Basis 2 mit 53 Bits Genauigkeit dargestellt werden kann, kann Python nicht produzieren genaues Ergebnis. Zum Beispiel ist 0.1 (in der Basis 10) eine unendliche Dezimalzahl in der Basis 2, 0.0001100110011 ..., so dass sie nicht genau dargestellt werden kann. Wenn Sie also auf einem Python-Prompt eingeben:

>>> 0.1 
0.10000000000000001 

Das Ergebnis Sie wieder zu bekommen ist anders, da hat sich von dezimal zu binär (mit 53 Bit Genauigkeit), zurück in Dezimalzahlen umgewandelt.Als Folge erhalten Sie Dinge wie diese:

>>> 0.1 + 0.2 == 0.3 
False 

Für eine gute (aber lang) lesen, What Every Programmer Should Know About Floating-Point Arithmetic sehen.

+1

+1 für '0.1 + 0.2 == 0.3'. Tolles, prägnantes Beispiel –

1

Siehe Handling very large numbers in Python.

Python hat eine BigNum Klasse für 200! und wird es automatisch verwenden.

Die Aussage Ihres Lehrers trifft zwar nicht genau zu, trifft aber im Allgemeinen zu. Computer haben Einschränkungen, und es ist gut zu wissen, was sie sind. Denken Sie daran, dass Sie jedes Mal, wenn Sie eine weitere Ganzzahl von Datenspeicher hinzufügen, eine Zahl speichern können, die 2^32 (4 Milliarden +) mal größer ist. Es ist schwer zu verstehen, wie viele weitere Zahlen das sind - aber Mathematik wird langsamer, wenn Sie weitere Ganzzahlen hinzufügen, um den genauen Wert einer sehr großen Zahl zu speichern.

Als Beispiel

>>> 2 << 1000 
2143017214372534641896850098120003621122809623411067214887500776740702102249872244986396 
7576313917162551893458351062936503742905713846280871969155149397149607869135549648461970 
8421492101247422837559083643060929499671638825347975351183310878921541258291423929553730 
84335320859663305248773674411336138752L 

ich, wie groß eine Zahl, die Sie mit 10000 Bits oder sogar 8.000.000 Bits (ein Megabyte), aber diese Zahl speichern zu illustrieren versucht (was man mit 1000 Bits speichern kann) ist viele Seiten lang.

+0

@Tom: Wie können Sie testen, dass Sie% 1 + 200 nicht tun können! %? Ich führe den folgenden Code erfolglos aus, obwohl 200! ist mehr als 2^32 größer als 1: http://dpaste.com/59409/ –

+0

Masi, ich denke durch "eine andere Ganzzahl von Speicher" Tom bedeutet "weitere 4 Bytes Speicherplatz" nicht eine andere tatsächliche Ganzzahl zu einem bestehenden hinzuzufügen ein. – MatrixFrog

+0

Das ist in der Tat, was ich meinte. Mein Punkt ist, dass es viele mögliche Kombinationen in einer sehr kleinen Menge an Speicher gibt. Zum Beispiel gibt es im Universum nur 10^69 Atome, eine Zahl, die kleiner als 2^230 ist (es gibt 256 Bytes in einer einzelnen L2-Cache-Zeile auf der Pentium 4-CPU). Stellen Sie sich vor, wie viele es in einem Megabyte Speicher gibt. –

2

Python hat unbegrenzte ganze Zahl Größen in Form von langen Typ. Das heißt, wenn es sich um eine ganze Zahl handelt, wird die Begrenzung der Größe der Zahl durch den für Python verfügbaren Speicher eingeschränkt.

Wenn Sie eine große Zahl wie 200 berechnen! und Sie sehen ein L am Ende davon, das bedeutet, Python hat den int automatisch in einen langen umgewandelt, weil ein int nicht groß genug war, um diese Zahl zu halten. Weitere Informationen finden Sie in Abschnitt 6.4 von this page.

+0

UND ... dafür ist keine "Approximation" erforderlich. –

+0

Übrigens, in Python 3.0 gibt es keinen Unterschied zwischen "normalen" ganzen Zahlen und "langen" ganzen Zahlen. Das System übersetzt nahtlos zwischen ihnen, so dass es keine Ls mehr gibt. – MatrixFrog

1

200! ist eine sehr große Anzahl in der Tat.

Wenn der IEEE-64-Bit-Bereich 1,7E +/- 308 (15 Ziffern) beträgt, können Sie sehen, dass der größte Faktor, den Sie erhalten können, 170 ist!

Python kann beliebig große Zahlen verarbeiten, genau wie Java mit seinem BigInteger.

+0

Keine Näherung. Genau. –

1

Ohne irgendeine Erklärung zu dieser Aussage ist es offensichtlich falsch. Nur aus persönlicher Erfahrung, frühe Lehren in der Programmierung (in den späten 1980er Jahren) beinhaltete die Lösung sehr ähnlicher, wenn nicht sogar genau die gleichen Probleme. Um ein Gerät zu kennen, das keine Berechnungen durchführt, muss man im Allgemeinen (im mathematischen Sinne eines Beweises) beweisen, dass dies nicht der Fall ist.

Pythons Integer-Typ (mit dem Namen int und long in 2.x, die beide in nur den int Typen in 3.x gefaltet) sind sehr gut, und sie überfluten nicht wie zum Beispiel des int Typen in C. Wenn Sie Machen Sie das Offensichtliche von print 200 * 199 * 198 * ... es kann langsam sein, aber es wird genau sein. Genauso sind Addition, Subtraktion und Modul genau. Division ist eine gemischte Tasche, da gibt es zwei Operatoren, / und //, und sie unterzog sich einer Änderung in 2.x — im Allgemeinen können Sie es nur als ungenau behandeln.

Wenn Sie mehr Kontrolle wollen und sich nicht auf Ganzzahlen beschränken möchten, sehen Sie sich das Modul decimal an.

1

Python behandelt große Zahlen automatisch (im Gegensatz zu einer Sprache wie C, in der die Datentypen überlaufen können und die Werte auf Null zurückgesetzt sind) - über einen bestimmten Punkt (sys.maxint oder 2147483647) konvertiert sie die ganze Zahl in eine "lange" (bezeichnet durch die L nach der Zahl), die beliebig lang sein kann:

>>> def fact(x): 
...  return reduce(lambda x, y: x * y, range(1, x+1)) 
... 
>>> fact(10) 
3628800 
>>> fact(200) 
788657867364790503552363213932185062295135977687173263294742533244359449963403342920304284011984623904177212138919638830257642790242637105061926624952829931113462857270763317237396988943922445621451664240254033291864131227428294853277524242407573903240321257405579568660226031904170324062351700858796178922222789623703897374720000000000000000000000000000000000000000000000000L 

Lange Zahlen sind „easy“, Gleitkommazahl ist komplizierter, und fast jede Computerdarstellung einer Gleitkommazahl ist eine Annäherung, Zum Beispiel:

>>> float(1)/3 
0.33333333333333331 

Natürlich kann man nicht eine unendliche Anzahl von 3s im Speicher speichern, so dass es betrügt und rundet es ein wenig ..

Sie können am decimal Modul aussehen soll:

  • Dezimalzahlen kann genau dargestellt werden. Im Gegensatz dazu haben Zahlen wie 1.1 keine exakte Darstellung im binären Fließkomma. Endbenutzer erwarten normalerweise nicht, dass 1.1 als 1.1000000000000001 angezeigt wird, wie dies bei binären Fließkommazahlen der Fall ist.
  • Im Gegensatz zu binären Gleitkomma-Hardware basierte, hat das Dezimalsystem Modul einen Benutzer änderbare Genauigkeit (bis 28 Plätze in Verzug), die als
  • für ein gegebenes Problem benötigt so groß sein kann
+0

@ dbr: Meinst du, dass, weil Python Binärzahlen verwenden muss, wir 1.1000000000000000000000000001 bekommen? –

+1

1.1 1 ist näher am tatsächlichen Wert, der vom Computer gespeichert wird, aber ab Python 3.1 vereinfachen sie die Darstellung, um es für Leute, die das nicht erkennen, weniger überraschend zu machen: http: // docs.python.org/dev/py3k/whatsnew/3.1.html – MatrixFrog

Verwandte Themen