Convertir cadena hexadecimal a int en Python


766

¿Cómo convierto una cadena hexadecimal a un int en Python?

Puedo tenerlo como " 0xffff" o simplemente " ffff".

Respuestas:


1087

Sin el prefijo 0x, debe especificar la base explícitamente, de lo contrario no hay forma de saber:

x = int("deadbeef", 16)

Con el prefijo 0x, Python puede distinguir hexadecimal y decimal automáticamente.

>>> print int("0xdeadbeef", 0)
3735928559
>>> print int("10", 0)
10

( Debe especificar 0como base para invocar este comportamiento de adivinación de prefijo; omitir el segundo parámetro significa asumir base-10).


25
Lo que significa que siempre debe usar 16 como segundo argumento. Explícito es mejor que implícito.
Bachsau

13
@bachsau, claramente falso. ¿Qué sucede si desea leer la entrada del usuario, permitiendo la entrada en hexadecimal o decimal, lo que sea conveniente para el usuario?
Dan Lenski el

77
Ok, debería haber dicho: ¡En este caso particular! La pregunta original era "¿Cómo convierto una cadena hexadecimal ...". Si desea dejarlo al usuario, entonces es una característica útil, con eso tiene razón.
Bachsau

@DanLenski, siempre convierte cadenas hexadecimales a números positivos. Quiero int("FFFF",16)convertirme a -1.
Nazar

@Nazar ha pasado mucho tiempo, por lo que es probable que esto no sea útil para usted en este momento, pero para cualquier otra persona que tropiece por aquí, si es necesario aplicar las reglas del complemento de los dos. Esta respuesta puede ayudar a stackoverflow.com/questions/1604464/twos-complement-in-python
Jeremy

163

int(hexString, 16) hace el truco y funciona con y sin el prefijo 0x:

>>> int("a", 16)
10
>>> int("0xa",16)
10


43

Convertir cadena hexadecimal a int en Python

Puedo tenerlo como "0xffff"o solo "ffff".

Para convertir una cadena en un int, pasa la cadena intjunto con la base desde la que estás convirtiendo.

Ambas cadenas serán suficientes para la conversión de esta manera:

>>> string_1 = "0xffff"
>>> string_2 = "ffff"
>>> int(string_1, 16)
65535
>>> int(string_2, 16)
65535

Dejar intinferir

Si pasa 0 como base, intinferirá la base del prefijo en la cadena.

>>> int(string_1, 0)
65535

Sin el prefijo hexadecimal, 0x, intno tiene suficiente información con la que adivinar:

>>> int(string_2, 0)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: invalid literal for int() with base 0: 'ffff'

literales:

Si está escribiendo en el código fuente o en un intérprete, Python hará la conversión por usted:

>>> integer = 0xffff
>>> integer
65535

Esto no funcionará ffffporque Python pensará que estás intentando escribir un nombre legítimo de Python en su lugar:

>>> integer = ffff
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name 'ffff' is not defined

Los números de Python comienzan con un carácter numérico, mientras que los nombres de Python no pueden comenzar con un carácter numérico.


Vale la pena repetir "Dejar int inferir Si pasa 0 como base, int inferirá la base del prefijo en la cadena". Cómo convertir de hexadecimal o decimal (o binario) a entero como lo hace el intérprete de Python.
gaoithe

13

Agregando a la respuesta de Dan anterior: si proporciona la función int () con una cadena hexadecimal, tendrá que especificar la base como 16 o no pensará que le dio un valor válido. No es necesario especificar la base 16 para los números hexadecimales no contenidos en las cadenas.

print int(0xdeadbeef) # valid

myHex = "0xdeadbeef"
print int(myHex) # invalid, raises ValueError
print int(myHex , 16) # valid

5

La peor manera:

>>> def hex_to_int(x):
    return eval("0x" + x)

>>> hex_to_int("c0ffee")
12648430

¡Por favor no hagas esto!

¿Usar eval en Python es una mala práctica?


3
Vale la pena señalar que evaltambién es absurdamente lento, además de todos los otros problemas con él.
j6m8

44
Si esta es una mala idea, ¿cuál es el punto de plantearla?
pppery

3
Buen punto. En parte porque creo que es divertido y en parte porque lo he visto en el código de producción.
André Laszlo

Probablemente debería tener en cuenta que solía hacer esto después de experimentar problemas con la int(s,16)devolución de valores incorrectos, causando algunos problemas importantes con mi tiempo de ejecución ( int(hex(value),16) == int(value) >>> False). la cadena suministrada a eval()era segura y el valor devuelto era correcto.
Tcll

1
Me pareció divertido e ilustrativo, me alegro de que se haya publicado
frogeyedpeas

3

O ast.literal_eval(esto es seguro, a diferencia eval):

ast.literal_eval("0xffff")

Manifestación:

>>> import ast
>>> ast.literal_eval("0xffff")
65535
>>> 

1

La opción de formateador '% x'% parece funcionar también en las declaraciones de asignación para mí. (Suponiendo Python 3.0 y posterior)

Ejemplo

a = int('0x100', 16)
print(a)   #256
print('%x' % a) #100
b = a
print(b) #256
c = '%x' % a
print(c) #100

Los comentarios son incorrectos. print(b)dará salida 256, no 100y print(c)dará salida 100, no 256. También tenga en cuenta que ces una cadena, pero ano es así, su respuesta en realidad convierte un int en una cadena, y no al revés (de esto se trata la pregunta).
André Laszlo

Gracias por su aporte, estoy de acuerdo en que mi respuesta no es correcta, y ahora la he solucionado. Sin embargo, me doy cuenta de que parte de la respuesta es redundante como anteriormente, es decir, usando int (string, base), pero aún así el resto de la respuesta agrega más opciones a la publicación, creo. De acuerdo ?
Soundararajan

Irrelevante; se trata de convertir de la base 16 a la base 10, no al revés
pppery

1

Si está utilizando el intérprete de Python, puede escribir 0x (su valor hexadecimal) y el intérprete lo convertirá automáticamente.

>>> 0xffff

65535

1

Maneja hexadecimal, octal, binario, int y flotante

Usando los prefijos estándar (es decir, 0x, 0b, 0 y 0o) esta función convertirá cualquier cadena adecuada a un número. Respondí esto aquí: https://stackoverflow.com/a/58997070/2464381 pero aquí está la función necesaria.

def to_number(n):
    ''' Convert any number representation to a number 
    This covers: float, decimal, hex, and octal numbers.
    '''

    try:
        return int(str(n), 0)
    except:
        try:
            # python 3 doesn't accept "010" as a valid octal.  You must use the
            # '0o' prefix
            return int('0o' + n, 0)
        except:
            return float(n)

-1

En Python 2.7, int('deadbeef',10)no parece funcionar.

Lo siguiente funciona para mí:

>>a = int('deadbeef',16)
>>float(a)
3735928559.0

44
¿Cómo responde esto a la pregunta?
pppery

-5

con el prefijo '0x', también puede usar la función eval

Por ejemplo

>>a='0xff'
>>eval(a)
255

16
Asegúrese de que la validación de entrada se realice correctamente si usa eval. De hecho, probablemente hay una mejor manera. No uses eval.
ALOToverflow

77
Por lo menos deberías estar usando ast.literal_eval.
Andy Hayden

2
También muy lento. La peor de todas.
Tõnu Samuel
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.