error UnicodeDecodeError: el códec 'utf-8' no puede decodificar el byte 0xff en la posición 0: byte de inicio no válido

164

https://github.com/affinelayer/pix2pix-tensorflow/tree/master/tools

Se produjo un error al compilar "process.py" en el sitio anterior.

 python tools/process.py --input_dir data --            operation resize --outp
ut_dir data2/resize
data/0.jpg -> data2/resize/0.png

Rastreo (llamadas recientes más última):

File "tools/process.py", line 235, in <module>
  main()
File "tools/process.py", line 167, in main
  src = load(src_path)
File "tools/process.py", line 113, in load
  contents = open(path).read()
      File"/home/user/anaconda3/envs/tensorflow_2/lib/python3.5/codecs.py", line 321, in decode
  (result, consumed) = self._buffer_decode(data, self.errors, final)
UnicodeDecodeError: 'utf-8' codec can't decode     byte 0xff in position 0: invalid start byte

¿Cuál es la causa del error? La versión de Python es 3.5.2.

tarta
fuente

Respuestas:

196

Python intenta convertir una matriz de bytes ( bytesque se supone que es una cadena codificada por utf-8) en una cadena unicode ( str). Este proceso, por supuesto, es una decodificación de acuerdo con las reglas utf-8. Cuando intenta esto, encuentra una secuencia de bytes que no está permitida en cadenas codificadas por utf-8 (es decir, este 0xff en la posición 0).

Como no proporcionó ningún código que pudiéramos ver, solo pudimos adivinar el resto.

A partir del seguimiento de la pila, podemos suponer que la acción desencadenante fue la lectura de un archivo ( contents = open(path).read()). Propongo recodificar esto de una manera como esta:

with open(path, 'rb') as f:
  contents = f.read()

Que ben el especificador de modo en los open()estados que el archivo se tratará como binario, entonces contentsseguirá siendo a bytes. Ningún intento de decodificación sucederá de esta manera.

Alfe
fuente
Recibo el error "ValueError: la cadena de modo debe comenzar con una de 'r', 'w', 'a' o 'U', no 'br'"
Unnikrishnan
3
@Unnikrishnan Ok, luego use rb(pensé que el orden no tenía importancia, pero parece ser, al menos en algunos sistemas / versiones). Cambié mi respuesta en consecuencia.
Alfe
57
byte 0xff in position 0también podría significar que el archivo está codificado en UTF-16, entonces puede hacerlo en su with open(path, encoding='utf-16') as f:lugar
Nikolai R Kristiansen
¿Qué pasa si en realidad no hay ningún 0xffpersonaje en la posición 0? Y está UTF-8codificado.
Iulian Onofrei
Un '\xFF'carácter puro se codificará en UTF-8 como '\xC3\xBF'. UTF-8 codifica todos los caracteres con un conjunto MSB usando dos caracteres. (Vea la salida de printf "\xff" | iconv -f latin1 -t utf-8 | xxden un shell.) Una palabra '\xFF'al comienzo de una cadena codificada UTF-8 es un error de codificación (podría llamarse un error de sintaxis en términos de UTF-8).
Alfe
83

Use esta solución, eliminará (ignorará) los caracteres y devolverá la cadena sin ellos. Solo use esto si su necesidad es despojarlos, no convertirlos.

with open(path, encoding="utf8", errors='ignore') as f:

Usando errors='ignore' Solo perderás algunos personajes. pero si no te importan, ya que parecen ser caracteres adicionales que se originan en un formato y programación incorrectos de los clientes que se conectan a mi servidor de socket. Entonces es una solución directa fácil. referencia

Nitish Kumar Pal
fuente
66
También funciona para decode (): contents = contents.decode('utf-8', 'ignore')Fuente: docs.python.org/3/howto/unicode.html#the-string-type
naaman
2
Debería ser la mejor respuesta
Statham
mejor solución en mi caso de uso :)
maestromusica
Cuando dice "perder algunos caracteres", ¿quiere decir que no se leerá el archivo con errores? o que no se leerá todo el contenido de ese archivo?
msoutopico
@msoutopico Como ignora los errores, no se leerán algunas codificaciones que causan problemas. Pero nunca he encontrado ningún contenido que se haya omitido durante la lectura. Entonces, básicamente, los problemas de ecoding se ignoran.
Nitish Kumar Pal
23

Tuve un problema similar a este, terminé usando UTF-16 para decodificar. Mi código está abajo.

with open(path_to_file,'rb') as f:
    contents = f.read()
contents = contents.rstrip("\n").decode("utf-16")
contents = contents.split("\r\n")

esto tomaría el contenido del archivo como una importación, pero devolvería el código en formato UTF. a partir de ahí sería decodificado y separado por líneas.

tattmoney76
fuente
10
En Python 3 puedes simplificar esto usando el parámetro de codificaciónwith open(path, encoding='utf-16') as f
Nikolai R Kristiansen
@NikolaiRKristiansen Intenté usar su método, pero recibí un error como TypeError: an integer is required (got type str). ¿Por qué? Ambos archivos son binarios y se leen como rb.
Bogotá
1
@Bogota El parámetro encodingsolo tiene sentido al leer texto. Suelte la 'b' del argumento de modo e intente nuevamente. Lea más en los documentos: docs.python.org/3/library/functions.html#open
Nikolai R Kristiansen
19

Use el formato de codificación ISO-8859-1 para resolver el problema.

Ramineni Ravi Teja
fuente
1
¡Finalmente llegué a esto después de probar más de 10 codificaciones!
Rexcirus
15

Me he encontrado con este hilo cuando sufro el mismo error, después de investigar un poco puedo confirmar, este es un error que ocurre cuando intentas decodificar un archivo UTF-16 con UTF-8.

Con UTF-16, el primer carácter (2 bytes en UTF-16) es una marca de orden de bytes (BOM) , que se utiliza como pista de decodificación y no aparece como un carácter en la cadena decodificada. Esto significa que el primer byte será FE o FF y el segundo, el otro.

Muy editado después de que descubrí la respuesta real

Peter Ogden
fuente
¡Esto terminó con 2 horas de dolor de cabeza! Abrir el archivo con abierto ('nombre de archivo', 'r') como f: y luego imprimir su contenido muestra UTF-8, lo cual es incorrecto.
nulldroid
4

Usar unicamente

base64.b64decode(a) 

en vez de

base64.b64decode(a).decode('utf-8')
pradeep karunathilaka
fuente
2
está funcionando pero solo para entender ¿puedes explicar por qué, por favor? :)
Ido Bleicher
3

Si está en una Mac, compruebe si tiene un archivo oculto, .DS_Store. Después de eliminar el archivo, mi programa funcionó.

Juan navarrete
fuente
1

Verifique la ruta del archivo a leer. Mi código seguía dándome errores hasta que cambié el nombre de la ruta para presentar el directorio de trabajo. El error fue:

newchars, decodedbytes = self.decode(data, self.errors)
UnicodeDecodeError: 'utf-8' codec can't decode byte 0xff in position 0: invalid start byte
Rex131xO
fuente
1

si está recibiendo datos de un puerto serie, asegúrese de estar usando la velocidad de transmisión correcta (y las otras configuraciones): decodificando usando ( utf-8 ) pero la configuración incorrecta generará el mismo error

UnicodeDecodeError: el códec 'utf-8' no puede decodificar el byte 0xff en la posición 0: byte de inicio no válido

para verificar la configuración del puerto serie en el uso de Linux: stty -F /dev/ttyUSBX -a

Saif Faidi
fuente
1

Simplemente significa que uno eligió la codificación incorrecta para leer el archivo.

En Mac, use file -I file.txtpara encontrar la codificación correcta. En Linux, use file -i file.txt.

Minh Triet
fuente
0

Tengo el mismo problema al procesar un archivo generado desde Linux. Resulta que estaba relacionado con archivos que contienen signos de interrogación.

Wim Folkerts
fuente
-1

Tuve un problema similar.

Resuelto por:

import io

with io.open(filename, 'r', encoding='utf-8') as fn:
  lines = fn.readlines()

Sin embargo, tuve otro problema. Algunos archivos html (en mi caso) no eran utf-8, por lo que recibí un error similar. Cuando excluí esos archivos html, todo funcionó sin problemas.

Entonces, excepto por arreglar el código, verifique también los archivos que está leyendo, tal vez haya una incompatibilidad allí.

Kostas Tsiligkiris
fuente
-5

Si es posible, abra el archivo en un editor de texto e intente cambiar la codificación a UTF-8. De lo contrario, hágalo programáticamente a nivel del sistema operativo.

Manoj Joshi
fuente
-5

Tengo un problema similar. Intento ejecutar un ejemplo en tensorflow / models / Objective_detection y encontré el mismo mensaje. Intenta cambiar Python3 a Python2

usuario8665083
fuente