Runden in Ironpython

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
spammi
User
Beiträge: 6
Registriert: Montag 30. März 2015, 14:59

Hallo zusammen, da es hier keine Unterforum zu Ironpython gibt, stelle ich meine Frage einfach mal hier. Da Ironpython auf Python 2.7 basiert, denke ich, dass man mir hier helfen kann.

Es geht darum, das ich Zahlen runden möchte (auf 5 Stellen), dass an und für sich ist kein Problem, wenn ich jedoch diese gerundeten Zahlen in eine Liste schreibe, dann hängt Python 999999.... oder ...00000001 hinten dran! :twisted:

Ich habe gelesen, dass es an float liegt und ich besser decimal verwenden sollte, dann habe ich es in decimal versucht, hat allederdings auch nicht funktioniert...

Hier der Code:

Code: Alles auswählen

v1=1
v2=-5
v = []
kw = []
while v1<vmax:
    kpv1 = math.sin(v1*y*math.pi/(yQ*2.0))
    kpv2 = math.sin(v2*y*math.pi/(yQ*2.0))
    kdv1 = math.sin(v1*q_P_P*alpha_u/2.0)/(q_P_P*math.sin(v1*alpha_u/2.0))
    kdv2 = math.sin(v2*q_P_P*alpha_u/2.0)/(q_P_P*math.sin(v2*alpha_u/2.0))
    v.append(v1)
    v.append(v2)
    kw1 = kpv1*kdv1
    kw2 = kpv2*kdv2
    print round(kw1,5)
    print round(kw2,5)
    kw.append(round(kw1,5))
    kw.append(round(kw2,5))
    v1 += 6
    v2 -=6
kpv1 = math.sin(v1*y*math.pi/(yQ*2.0))
kdv1 = math.sin(v1*q_P_P*alpha_u/2.0)/(q_P_P*math.sin(v1*alpha_u/2.0))
v.append(v1)
kw.append (kpv1*kdv1)
print v 
print kw
die Ausgabe war folgende:
0.96593
-0.25882
0.25882
-0.96593
-0.96593
0.25882
-0.25882
0.96593
[1, -5, 7, -11, 13, -17, 19, -23, 25]
[0.96592999999999996, -0.25881999999999999, 0.25881999999999999, -0.96592999999999996, -0.96592999999999996, 0.25881999999999999, -0.25881999999999999, 0.96592999999999996, 0.96592582628906842]
Wie man sieht: Runden funktioniert, aber nicht wieder in die Liste schreiben!
dann habe ich folgendes geändert:

Code: Alles auswählen

kwform = ['%.5f' % elem for elem in kw]
print v 
print kwform
folgende Ausgabe:
0.96593
-0.25882
0.25882
-0.96593
-0.96593
0.25882
-0.25882
0.96593
[1, -5, 7, -11, 13, -17, 19, -23, 25]
['0.96593', '-0.25882', '0.25882', '-0.96593', '-0.96593', '0.25882', '-0.25882', '0.96593', '0.96593']
Jetzt stören mich aber die '' bei den Zahlen und ich habe nun ja auch strings und keine floats/decimals mehr...
Es gibt bestimmt eine Lösung.

Danke schon mal für eure Hilfe.
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

spammi hat geschrieben:Hallo zusammen, da es hier keine Unterforum zu Ironpython gibt, stelle ich meine Frage einfach mal hier. Da Ironpython auf Python 2.7 basiert, denke ich, dass man mir hier helfen kann.
Passt schon! Tatsächlich ist IronPython ja nur eine Implementierung der Sprache Python - Genauso wie Jython oder PyPy :-)
spammi hat geschrieben: ... wenn ich jedoch diese gerundeten Zahlen in eine Liste schreibe, dann hängt Python 999999.... oder ...00000001 hinten dran! :twisted:
Nö! Das passiert nicht durch das Anhängen an eine Liste, sondern bereits durch das Runden! ``float``-Zahlen haben eben nur eine begrenzte Auflösung... wenn Du das genauer brauchst, musst Du tatsächlich ``decimal`` verwenden.
spammi hat geschrieben: Jetzt stören mich aber die '' bei den Zahlen und ich habe nun ja auch strings und keine floats/decimals mehr...
Das ist ja nur die *Darstellung* von String Literalen! Du kannst die Elemente ja mal printen, dann wirst Du sehen, dass da keine Anführungszeichen mehr auftauchen:

Code: Alles auswählen

In [15]: s = "Hallo Welt!"

In [16]: s
Out[16]: 'Hallo Welt!'

In [17]: print(s)
Hallo Welt!
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Sirius3
User
Beiträge: 17754
Registriert: Sonntag 21. Oktober 2012, 17:20

@spammi: float speichert intern eine Binärdarstellung der Zahl. Wenn Du dezimal rundest ist das nicht mehr exakt darstellbar. Dich sollte auch gar nicht interessieren, was da wie intern gespeichert wird.
Was ist bei Dir der Zweck des Rundens? Wenn Du nur eine "schöne" Darstellung willst, solltest Du die Ausgabeformatierung benutzen, wie Du sie ja auch schon entdeckt hast: '%.5f'.
Die Ausgabe einer Liste ist sowieso nur für Debugzwecke da und da sollte es einen nicht stören, dass die exakte Darstellung einer Zahl gewählt wird.
spammi
User
Beiträge: 6
Registriert: Montag 30. März 2015, 14:59

Sirius3 hat geschrieben: Was ist bei Dir der Zweck des Rundens?
Ich lass die Werte der Liste in eine txt Datei schreiben, um sie nachher mit Excel weiterzuverarbeiten und das gefällt mir einfach besser wenn die Spalten in Excel nicht so ewig lang werden. Man könnte natürlich auch mit Excel runden, aber ich bin faul und mag VBA nicht. Am liebsten würde ich Numpy verwenden, aber das funktioniert leider nicht mit Ironpython, deswegen Excel.

@Hyperion: Es geht mir nicht um die Genauigkeit, sondern nur darum, nicht so "lange" Zahlen zu haben. Gibt es denn eine Möglichkeit die floats/decimals zu Runden ohne dieser vorher in Strings zu wandeln, weil dann müsste ich ja diese wieder in floats wandeln... Kann man denn komplette Listen casten oder müsste ich dann mit einer Schleife jedes einzelne Element casten?
BlackJack

@spammi: Ich denke Du hast das Problem nicht verstanden denn wenn Du so eine ”kurze” Zeichenkettendarstellung einer Gleitkommazahl danach wieder in eine Gleitkommazahl wandelst, dann sind auch die zusätzlichen Nachkommastellen wieder da. Und um die Zahlen in eine *Text*datei zu schreiben *musst* Du sie ja in Zeichenketten umwandeln, also ist das auch der Zeitpunkt an dem man dafür sorgt das nur die gewünschte Anzahl von Nachkommastellen in der Datei landen.

Man kann keine kompletten Listen ”casten”. Du kannst eine Schleife verwenden, oder eine „list comprehension”, oder einen Generatorausdruck, oder eine Funktion wie `map()` oder `itertools.imap()`, oder…
Sirius3
User
Beiträge: 17754
Registriert: Sonntag 21. Oktober 2012, 17:20

@spammi: um in Excel Zahlen mit nur einer gewissen Anzahl an Nachkommastellen darzustellen braucht man weder VBA noch irgendetwas zu runden. Man stellt einfach das Zahlenformat auf '#.00000', denn auch Excel rechnet intern mit floats, die 54bit Genauigkeit haben.
spammi
User
Beiträge: 6
Registriert: Montag 30. März 2015, 14:59

Sirius3 hat geschrieben:@spammi: um in Excel Zahlen mit nur einer gewissen Anzahl an Nachkommastellen darzustellen braucht man weder VBA noch irgendetwas zu runden. Man stellt einfach das Zahlenformat auf '#.00000', denn auch Excel rechnet intern mit floats, die 54bit Genauigkeit haben.
Danke für den Hinweis, kannst du mir auch sagen wie ich das mache?
Antworten