Python: Convert hex string to int and back

14,921

Solution 1

def str_to_int(s):
    i = int(s, 16)
    if i >= 2**23:
        i -= 2**24
    return i

def int_to_str(i):
    return '%06x'%((i+2**24)%2**24)

Test results:

In [36]: str_to_int('012345')
Out[36]: 74565

In [37]: str_to_int('fedcba')
Out[37]: -74566

In [38]: int_to_str(74565)
Out[38]: '012345'

In [39]: int_to_str(-74566)
Out[39]: 'fedcba'

Reference: Hex string to signed int in Python 3.2?

Solution 2

(Edit: An oversight on my part. See Rob's answer for correctly covering the negative sign numbers)

If you just want to convert a hex string into an int, do e.g.:

>>> int('0xff', 16)
255
>>> int('0xdaad', 16)
55981

The reverse can be done with the hex() function. From the help page:

Help on built-in function hex in module builtins:

>>> help(hex)
hex(...)
    hex(number) -> string

    Return the hexadecimal representation of an integer.

       >>> hex(3735928559)
       '0xdeadbeef'

It should be trivial to remove or add the '0x' if it's missing in your data stream. Here's an example to ensure padding to 6 chars (representing 3 bytes = 24 bits):

>>> '0x' + hex(255)[2:].rjust(6, '0')
'0x0000ff'

If you get the data in 3 byte form (24 bits), you can use int.to_bytes() and int.from_bytes() as described in the Python docs. This is new in Python 3.2.

Solution 3

$ pip install bitstring

Then:

from bitstring import BitStream
s1 = BitStream('0x012345')
s1.int # 74565
s2 = BitStream(int=-74565, length=24)
s2.hex # fedcbb
Share:
14,921
guo
Author by

guo

Updated on June 04, 2022

Comments

  • guo
    guo almost 2 years

    My python script gets and sends words over a serial line. Each word is a signed 24-bit value, received as hex string. The script should now take these strings and convert them to integers, do some calculations on it, and send them back in the same format. My problem is, how to do this conversion

    Examples
    
    Rx string -> calc int
     012345   ->  74565
     fedcba   -> -74566
    
    calc int -> Tx string
      74565  -> 012345
     -74566  -> fedcba
    

    How can this be done?