Seite 1 von 1
grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 09:11
von lagerschaden
Python kann ja mit sehr grossen Zahlen umgehen, aber da scheint es Unterschiede zwischen Python2 und Python3 zu geben. Das nachfolgende Beispiel läuft mit Python2 auch mit 6-stelligen Werten für p problemlos durch, während Python3 schon bei p=8 mit einer Fehlermeldung aufgibt.
Code: Alles auswählen
#!/usr/bin/python2
# -*- coding: utf-8 -*-
# berechnet die p-te Potenz von start durch Multiplikation
# und rechnet durch Division wieder zurueck, Ergebnis muss
# dann gleich start sein
p = 8
start = 8648234678954023643289846329847304534823
sum = start
for i in range(p):
sum = sum * start
for i in range(p):
sum = sum / start
print(sum)
print(start)
Fehlermeldung:
Code: Alles auswählen
Traceback (most recent call last):
File "./sum.py", line 17, in <module>
sum = sum / start
OverflowError: integer division result too large for a float
Re: grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 09:32
von nezzcarth
Der Traceback gibt schon einen ersten Hinweis, den du leicht im Interpreter überprüfen kannst:
Code: Alles auswählen
Python 3.7.4 (default, Jul 16 2019, 07:12:58)
[GCC 9.1.0] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> 5/2
2.5
>>> 5//2
2
Code: Alles auswählen
Python 2.7.16 (default, Mar 11 2019, 18:59:25)
[GCC 8.2.1 20181127] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> 5/2
2
>>> 5//2
2
>>> from __future__ import division
>>> 5/2
2.5
Übrigens existieren analog zur Inkrementierung 'i += 1' auch die Operatoren 'i /= 2' und 'i //= 2'.
Re: grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 09:55
von lagerschaden
In dem obigen Beispiel ist sum während das Programmablaufes immer eine ganze Zahl, Python3 rechnet dann also bei der Division im Gegensatz zu Python2 nicht ganz korrekt, weil offensichtlich eine Umwandlung in float stattfindet.
Ich habe mal ein print(sum) eingefügt, dann rechnet Python3 bei der Multiplikation auch bei grossen Werten mit Integer und ab der 1. Division mit Float obwohl die Zahl immer eine ganze Zahl ist. Ist die Zahl zu gross, steigt Python3 mit der Fehlermeldung aus während Python2 das locker managed.
Hat das denn einen Vorteil, dass Python3 eine extra Integer-Division hat? Bei nicht zu grossen Zahlen macht Python3 es ja auch richtig.
Code: Alles auswählen
#!/usr/bin/python3
# -*- coding: utf-8 -*-
# berechnet die p-te Potenz von start durch Multiplikation
# und rechnet durch Division wieder zurueck, Ergebnis muss
# dann gleich start sein
p = 999
start = 8648234678954023643289846329847304534823
sum = start
for i in range(p):
sum = sum * start
print(sum)
for i in range(p):
sum = sum / start
print(sum)
print(sum)
print(start)
Re: grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 10:00
von Sirius3
Das hat den Vorteil, dass viele bei der Division erwarten, dass bei 3/2 das selbe Ergebnis kommt wie bei 3./2. Ganzzahldivision ist eine andere Operation und das Ergebnis sollte nicht vom Typ der Operanden abhängen.
Warum programmierst Du start**p nach und nennst das Ergebnis sum?
Re: grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 10:04
von lagerschaden
Das bedeutet aber, dass gerade bei der aktuellen Umstellung auf Python3 vieles in die Hose geht (das genau ist mir passiert), weil das Verhalten der Division bei kleinen und grossen Zahlen unterschiedlich ist, wie man in meinem Beispiel sieht. Übrigens meckert 2to3 das nicht an, kann es auch nicht, da es nicht weiss, ob Integer oder Float bzw. die Zahlengrösse.
Die Bezeichnung sum stammt aus dem grösseren Projekt, da ist es auch eine Summe. Ich habe hier nur ein Snippet gezeigt.
Re: grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 10:05
von nezzcarth
lagerschaden hat geschrieben: Sonntag 6. Oktober 2019, 09:55
In dem obigen Beispiel ist sum während das Programmablaufes immer eine ganze Zahl, Python3 rechnet dann also bei der Division im Gegensatz zu Python2 nicht ganz korrekt, weil offensichtlich eine Umwandlung in float stattfindet.
Ich habe mal ein print(sum) eingefügt, dann rechnet Python3 bei der Multiplikation auch bei grossen Werten mit Integer und ab der 1. Division mit Float obwohl die Zahl immer eine ganze Zahl ist. Ist die Zahl zu gross, steigt Python3 mit der Fehlermeldung aus während Python2 das locker managed.
Wenn ich dich richtig verstehe, wäre dein Vorschlag, dass 4/2 einen Integer ergibt, weil das Ergebnis eine Ganzzahl ist, 4/3 aber einen Float? Das wäre aus meiner Sicht eine schlechte Lösung, da dann der Typ schlecht vorhersagbar ist. Die beiden denkbaren Alternativen sind, dass Division-Ergebnisse entweder konsistent Integer, oder konsistent Floats sind. Und in der Wahl dieser beiden Varianten unterscheiden sind Python2 und Python3. Ich kenne die Begründung der Python Entwickler für diese Design-Entscheidung nicht, aber aus meiner Sicht ist die Art und Weise, wie Python3 es handhabt sinnvoller, denn es geht nichts verloren. 4/3 ist für Python2 1 und wenn ich das in einen Float konvertiere, bleibt es 1.0. 4/2 Ist für Python3 2.0 und wenn ich es in einen Integer konvertiere ist es immer noch 2.
Re: grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 10:10
von Sirius3
@lagerschaden: welche Art der Division du brauchst hängt halt davon ab was du an der Stelle tun willst. Das kann man nur händisch an jeder Stelle im Code entscheiden. Zum Glück versteht python2 dank future-Import die neue Syntax und Du siehst schnell anhand Deiner Unit-Tests ob alles mit der neuen Syntax noch läuft.
Re: grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 10:12
von lagerschaden
Dass 4/3 für Python2 nicht 1.333 sondern 1 ergibt, wissen wir ja aus der Erfahrung und haben das entsprechend berücksichtigt.
Das neue Verhalten von Python3 macht bei der Umstellung von 2 auf 3 aber grosse Probleme, ich habe an diesem Projekt mehrere Tage gebraucht, nur um diesen 1 Fehler zu finden. Ich werde also alte Projekte vermutlich gar nicht umstellen sondern nur neue Projekte mit Python3 beginnen.
Vielen Dank an Euch für die Hilfe.
Re: grosse Zahlen - Unterschied Python2 und Python3
Verfasst: Sonntag 6. Oktober 2019, 10:18
von nezzcarth
lagerschaden hat geschrieben: Sonntag 6. Oktober 2019, 10:12
Ich werde also alte Projekte vermutlich gar nicht umstellen sondern nur neue Projekte mit Python3 beginnen.
Dabei solltest du aber berücksichtigen, dass der Python2 Support Ende des Jahres ausläuft. Das bedeutet zwar natürlich nicht, dass der Python2 Interpreter unverzüglich die Arbeit verweigert, aber es wird zunehmend schwerer, ihn noch (zum Laufen) zu bekommen, da es keine offiziellen Versionen mehr geben wird. Er wird nach und nach aus den offiziellen Repositorien der Linux Distributionen verschwinden und auch auf zukünftigen Windows Versionen möglicherweise nicht mehr ausführbar sein. Software ohne (Sicherheits)updates ist ein Problem.