Extraigo datos de un documento de Google, los proceso y los escribo en un archivo (que eventualmente pegaré en una página de Wordpress).
Tiene algunos símbolos no ASCII. ¿Cómo puedo convertirlos de manera segura en símbolos que se pueden usar en código fuente HTML?
Actualmente estoy convirtiendo todo a Unicode en el camino, uniéndolo todo en una cadena de Python, y luego haciendo:
import codecs
f = codecs.open('out.txt', mode="w", encoding="iso-8859-1")
f.write(all_html.encode("iso-8859-1", "replace"))
Hay un error de codificación en la última línea:
UnicodeDecodeError: el códec 'ascii' no puede decodificar el byte 0xa0 en la posición 12286: el ordinal no está en el rango (128)
Solución parcial:
Este Python se ejecuta sin error:
row = [unicode(x.strip()) if x is not None else u'' for x in row]
all_html = row[0] + "<br/>" + row[1]
f = open('out.txt', 'w')
f.write(all_html.encode("utf-8"))
Pero luego, si abro el archivo de texto real, veo muchos símbolos como:
Qur’an
¿Quizás necesito escribir en algo que no sea un archivo de texto?
Respuestas:
Trate exclusivamente con objetos unicode tanto como sea posible decodificando cosas en objetos unicode cuando los obtenga por primera vez y codificándolos según sea necesario al salir.
Si su cadena es en realidad un objeto Unicode, deberá convertirla en un objeto de cadena codificada Unicode antes de escribirla en un archivo:
Cuando vuelva a leer ese archivo, obtendrá una cadena codificada en Unicode que puede decodificar en un objeto Unicode:
fuente
En Python 2.6+, puede usar
io.open()
el valor predeterminado ( integradoopen()
) en Python 3:Puede ser más conveniente si necesita escribir el texto de forma incremental (no necesita llamar
unicode_text.encode(character_encoding)
varias veces). A diferencia delcodecs
módulo, elio
módulo tiene un soporte de líneas nuevas universal adecuado.fuente
El manejo de cadenas Unicode ya está estandarizado en Python 3.
Solo necesita abrir el archivo en utf-8
(la conversión de Unicode de 32 bits a longitud de byte variable utf-8 se realiza automáticamente de la memoria al archivo).
fuente
El archivo abierto por
codecs.open
es un archivo que tomaunicode
datos, los codificaiso-8859-1
y los escribe en el archivo. Sin embargo, lo que intentas escribir no lo esunicode
; lo tomasunicode
y lo codificas eniso-8859-1
ti mismo . Eso es lo que hace elunicode.encode
método, y el resultado de codificar una cadena Unicode es una cadena de bytes (unstr
tipo).Debe usar normal
open()
y codificar el Unicode usted mismo, o (generalmente una mejor idea) usarcodecs.open()
y no codificar los datos usted mismo.fuente
Prefacio: ¿funcionará su visor?
Asegúrese de que su visor / editor / terminal (sin embargo, está interactuando con su archivo codificado utf-8) pueda leer el archivo. Esto es frecuentemente un problema en Windows , por ejemplo, el Bloc de notas.
En Python 2, use
open
desde elio
módulo (esto es lo mismo que el incorporadoopen
en Python 3):Las mejores prácticas, en general, se utilizan
UTF-8
para escribir en archivos (ni siquiera tenemos que preocuparnos por el orden de bytes con utf-8).utf-8 es la codificación más moderna y universalmente utilizable: funciona en todos los navegadores web, en la mayoría de los editores de texto (consulte su configuración si tiene problemas) y en la mayoría de los terminales / shells.
En Windows, puede intentarlo
utf-16le
si está limitado a ver la salida en el Bloc de notas (u otro visor limitado).Y solo ábralo con el administrador de contexto y escriba sus caracteres Unicode:
Ejemplo usando muchos caracteres Unicode
Aquí hay un ejemplo que intenta asignar todos los caracteres posibles de hasta tres bits de ancho (4 es el máximo, pero eso iría un poco lejos) de la representación digital (en enteros) a una salida imprimible codificada, junto con su nombre, si posible (poner esto en un archivo llamado
uni.py
):Esto debería ejecutarse en el orden de aproximadamente un minuto, y puede ver el archivo de datos, y si su visor de archivos puede mostrar unicode, lo verá. La información sobre las categorías se puede encontrar aquí . Según los recuentos, probablemente podamos mejorar nuestros resultados al excluir las categorías Cn y Co, que no tienen símbolos asociados.
Mostrará el mapeo hexadecimal, la categoría , el símbolo (a menos que no pueda obtener el nombre, por lo que probablemente sea un carácter de control) y el nombre del símbolo. p.ej
Recomiendo
less
en Unix o Cygwin (no imprimir / cat el archivo completo a su salida):por ejemplo, se mostrará de manera similar a las siguientes líneas que probé usando Python 2 (Unicode 5.2):
Mi Python 3.5 de Anaconda tiene unicode 8.0, supongo que la mayoría de los 3 lo harían.
fuente
Cómo imprimir caracteres Unicode en un archivo:
Guarde esto en el archivo: foo.py:
Ejecútelo y canalice la salida al archivo:
Abra tmp.txt y mire adentro, verá esto:
Por lo tanto, ha guardado unicode e con una marca de ofuscación en un archivo.
fuente
Ese error surge cuando intenta codificar una cadena no unicode: intenta decodificarla, suponiendo que esté en ASCII simple. Hay dos posibilidades:
f.write(all_html)
lugar..encode(...)
, primero intenta decodificarlo.fuente
En caso de escribir en python3
En caso de escribir en python2:
Para evitar este error, tendría que codificarlo en bytes usando códecs "utf-8" como este:
y decodifique los datos mientras lee utilizando los códecs "utf-8":
Y también si intenta ejecutar la impresión en esta cadena, se decodificará automáticamente utilizando los códecs "utf-8" como este
fuente