Soy incapaz de convertir los siguientes Unicode a ASCII sin perder los datos:

u'ABRA\xc3O JOS\xc9'

Traté de encode y decode y ellos no lo hacen.

¿Alguien tiene una sugerencia?

  • ¿Usted realmente necesita para la codificación en ASCII, o simplemente para «algunos caracteres de 8-bits» o «mi plataforma de 8 bits por defecto del juego de caracteres» o algo por el estilo?
  • Fue a ASCII. La conexión de base de datos se establece como ASCII.
  • Para su referencia, la cadena de caracteres de Unicode se parece a ABRAHAM JOSÉ

2 Comentarios

  1. 38

    Los caracteres Unicode u'\xce0' y u'\xc9' no tienen ningún ASCII correspondientes valores. Por lo tanto, si usted no quiere perder sus datos, usted tiene que codificar los datos en alguna forma que sea válida como ASCII. Las opciones incluyen:

    >>> print s.encode('ascii', errors='backslashreplace')
    ABRA\xc3O JOS\xc9
    >>> print s.encode('ascii', errors='xmlcharrefreplace')
    ABRAÃO JOSÉ
    >>> print s.encode('unicode-escape')
    ABRA\xc3O JOS\xc9
    >>> print s.encode('punycode')
    ABRAO JOS-jta5e

    Todos estos son cadenas de caracteres ASCII, y contener toda la información original de su cadena de Unicode (de modo que todos ellos se puede invertir sin pérdida de datos), pero ninguno de ellos son todos los que bastante para que un usuario final (y ninguno de ellos puede ser revertida sólo por decode('ascii')).

    Ver str.codificar, Específico De Python Codificaciones, y Unicode HOWTO para obtener más información.


    Como una nota del lado, cuando la gente dice «ASCII», que en realidad no significa «ASCII», sino «cualquier caracteres de 8 bits, que es un superconjunto de ASCII» o «algunos caracteres de 8-bits set que tengo en mente». Si eso es lo que significaba, la solución es codificar el derecho de caracteres de 8 bits set:

    >>> s.encode('utf-8')
    'ABRA\xc3\x83O JOS\xc3\x89'
    >>> s.encode('cp1252')
    'ABRA\xc3O JOS\xc9'
    >>> s.encode('iso-8859-15')
    'ABRA\xc3O JOS\xc9'

    La parte difícil es saber qué conjunto de caracteres que significaba. Si usted está escribiendo el código que produce el 8-cadenas de bits y el código que la consume, y no conocen nada mejor, que significaba UTF-8. Si el código que consume el 8-cadenas de bits es, digamos, el open función o un navegador web que usted está sirviendo a una página o algo, las cosas son más complicadas, y no existe una respuesta fácil, sin mucha más información.

    • Impresionante respuesta.
    • Gracias. Que ha ayudado. Yo ya había hecho la xmlcharrefreplace pero como yo estaba escribiendo a una de Oracle DB, es poner la basura en mi cadena. He solucionado el problema cambiando el NLS_LANG param. os.environ["NLS_LANG"] = "AMERICAN_AMERICA.WE8ISO8859P1" y, a continuación, convertir a los «latin-1»
    • Tenga en cuenta que, a pesar de Latin-1/ISO-8859-1 se ocupa tanto de tus personajes, no manejan la mayoría de Unicode. Así que, tan pronto como alguien que trata de darle un ruso o un Chino de nombre, usted obtendrá un UnicodeError. Si se puede configurar Oracle para el uso de UTF-8 en lugar de eso, usted va a evitar tales problemas en el futuro. Si no se puede… solo ten en mente, y el diseño de las pruebas en consecuencia.
    • Punycode para ganar!
  2. 0

    Necesitaba calcular el MD5 hash de un unicode string recibido en HTTP request. MD5 estaba dando UnicodeEncodeError y python basado en la codificación de los métodos no funciona porque reemplaza los caracteres de la cadena, con la correspondiente hex values para los personajes cambiando así la MD5 hash.
    Así que se me ocurrió el siguiente código, que mantiene la cadena intacta, mientras que la conversión de unicode.

    unicode_string = ''.join([chr(ord(x)) for x in unicode_string]).strip()

    Esto elimina la unicode parte de la cadena y guarda todos los datos intactos.

Dejar respuesta

Please enter your comment!
Please enter your name here