Python Dezimal und Hexadezimal berechnen?
Guten Tag,
Ich bin seit geraumer Zeit an einer Aufgabe dran, aber ich komme leider nicht weiter. Ziel ist es, wie schon im Titel erwähnt, Dezimal und Hexadezimalzahlen zu berechnen, die als Input aus einer txt file kommen. Wir dürfen aber nicht die Built-in-functions benutzen, sondern müssen eigene schreiben, die einen gewissen Algorithmus benutzen, um diese zu berechnen.
Für Hexadezimalzahlen in Dezimal ist es folgender Algorithmus: d1*16n−1 + d2*16n−2 + ... + dn*160, 0 <= di< 16
Und andersrum:
314156 // 16 = 19634 balance 12 (C)
19634 // 16 = 1227 balance 2 (2)
1227 // 16 = 76 balance 11 (B)
76 // 16 = 4 balance 12 (C)
4 // 16 = 0 balance 4 (4)
Hence, 31415610= 0x4CB2C
Leider bin ich ziemlich verloren und weiß nicht wie ich die beiden Algorithmen in zwei Funktionen verpacken soll um diese zu berechnen. Hoffe hier kann mir jemand helfen.
Vielen Dank im Vorraus.
2 Antworten
Du musst eine Schleife aufsetzen deren Rest immer kleiner wird und nur solange läuft wie der Rest noch größer als 16 ist (DEZ ->Hex Wandlung)
Dürft ihr keine "Mathe-Bibliothek" verwenden. So etwas gibt es natürlich schon von anderen gelöst und zur Verfügung gestellt.
Was ist mit diesem "Strukt Pack"
Umrechnen einer Zahl in Hexformat - Das deutsche Python-Forum (python-forum.de)
ABER:
Die Umrechnung ist wirklich nicht schwierig selbst zu programmieren und ne schöne Übung.
Denn du kannst dann gleich HEX->BIN; HEX->DEZ; DEZ->HEX; DEZ->BIN analog erledigen.
Letztlich muß DU nur den Algorithmus abbilden.
Machen wir erstmal Hexadezimal zu Dezimal, nehmen wir eine Zahl wie:
2FFA
Die Stellen entsprechen von rechts nach links 16^0, 16^1, 16^2 usw. .
Meine Zahl ergibt sich also aus 2*16^3+F*16^2+F*16^1+A*16^0. Merke, daß der größte Exponent um 1 kleiner als die Länge des Strings ist.
Nun habe ich generell unterschiedliche Möglichkeiten vorzugehen. Schauen wir zunächst auf ein Teilproblem, ich muß die einzelnen Stellen in ihre dezimalen Gegenstücke konvertieren, das kann ich in Python ganz bequem mit einem Dictionary lösen:
hex2dec={'0':0,'1':1,'a':10,'f':15}
Exemplarisch, natürlich muß Du alle 15 Hexziffern im Dict haben. Das bequeme dabei ist, daß ich mit dem in-Operator gleich auch prüfen kann, ob die Ziffenr im Wertebereich liegen.
------
Wir können also nun die Länge des Strings bestimmen, um den größten Exponenten zu bestimmen und dann einfach in einer Schleife die oben gezeigte Rechnung ausführen, indem wir die Ziffer konvertieren, mit dem 16^x multiplizieren und alles aufsummieren.
Wir können das aber auch machen, ohne die Länge zu kennen:
>>> hex='23FF9A1'
>>> for digit in reversed(hex):
... print(digit)
...
1
A
9
F
F
3
2
Wir laufen die Ziffern in ungekehrter Reihenfolge ab und zählen stattdessen den Exponenten hoch.
e=0
result=0
for digit in reversed(hexstring):
result+=mydict[digit]*math.pow(16,e)
e+=1
Kommen wir zu einer weiteren Methode, bei der ich die Länge nicht kennen muß und sogar ohne Potenzieren auskommen, ich demonstriere das nochmal an der Beispielzahl:
2*16^3+F*16^2+F*16^1+A*16^0
Wenn ich nun Mit 0 Anfange mit 16 multipliziere und 2 addiere, mit 16 Multipliziere und F addiere, mit 16 multipliziere usw. usf. . Dann erhalte ich
(((2*16)+F)*16+F)*16)+A
Was genau der Darstellung mit Potenzen nach Ausmultiplizieren entspricht.
Der Vorteil dieses Ansatzes ist, daß er mit einfacher Multiplikation und Addition auskommt.
Algorithmisch sieht das dann etwa so aus:
result=0
for digit in hexstring:
result*=16
result+=hex2dec(digit)
Hier ohne Gültigkeitsprüfung und unter der Annahme, daß hex2dec eine Hexziffer zu einem Dezimalwert umwandelt (Umsetzung wie gezeigt über Dictionary).
------
Die Umkehrung der letzten Variante ist dann das wiederholte dividieren durch 16, bequem in diesem Zusammenhang ist
>>> divmod(1240,16)
(77, 8)
Die Ganzzahldivision mit Rest.
>>> val=8712389
>>> while val>0:
... val,r=divmod(val,16)
... print(r)
...
5
12
0
15
4
8
>>> hex(8712389)
'0x84f0c5'
Wie Du siehst erzeugt die Schleife 5, C, 0, F, 5 ,8
Ich erzeuge vorzugsweise wieder ein Dictionary, diesmal mit int zu Dezimalzifern:
d={1:'1',2:'2',...,10:'A',...,15:'F'}
Und baue mir aus den Zeichen dann den String, indem ich vorne den konvertierten Dezimalwert anhänge.
Doch, Mathe-Bibliotheken dürfen wir verwenden. Die einzige Einschränkung bezieht sich auf die eingebauten Funktionen. Echt? Gibt es da schon Beispiele? Als ich dazu recherchiert habe, habe ich leider nichts gefunden.