erro UnicodeDecodeError: o codec 'utf-8' não pode decodificar o byte 0xff na posição 0: byte inicial inválido


162

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

Ocorreu um erro ao compilar "process.py" no site acima.

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

Traceback (última chamada mais recente):

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

Qual é a causa do erro? A versão do Python é 3.5.2.

Respostas:


194

O Python tenta converter um byte-array ( bytesque ele supõe ser uma string codificada em utf-8) em uma string unicode ( str). Esse processo, é claro, é uma decodificação de acordo com as regras do utf-8. Quando tenta isso, encontra uma sequência de bytes que não é permitida em seqüências de caracteres codificadas em utf-8 (ou seja, este 0xff na posição 0).

Como você não forneceu nenhum código que pudéssemos analisar, só conseguimos adivinhar o resto.

A partir do rastreamento da pilha, podemos assumir que a ação acionadora foi a leitura de um arquivo ( contents = open(path).read()). Proponho recodificar isso de uma maneira como esta:

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

Que bno especificador de modo nos open()estados em que o arquivo deve ser tratado como binário, contentspermanecerá a bytes. Nenhuma tentativa de decodificação acontecerá dessa maneira.


Estou recebendo o erro "ValueError: string de modo deve começar com 'r', 'w', 'a' ou 'U', não 'br'"
Unnikrishnan

3
@Unnikrishnan Ok, então use rb(eu pensei que a ordem não era importante, mas parece ser, pelo menos em alguns sistemas / versões). Mudei minha resposta de acordo.
Alfe

57
byte 0xff in position 0Também poderia significar o arquivo está codificado em UTF-16, então você pode fazer with open(path, encoding='utf-16') as f:em vez
Nikolai R Kristiansen

E se realmente não houver um 0xffpersonagem na posição 0? E é UTF-8codificado.
Iulian Onofrei 02/09/19

Um '\xFF'caractere puro será codificado em UTF-8 como '\xC3\xBF'. UTF-8 codifica todos os caracteres com um conjunto MSB usando dois caracteres. (Veja a saída de printf "\xff" | iconv -f latin1 -t utf-8 | xxdem um shell.) Um texto literal '\xFF'no início de uma cadeia codificada em UTF-8 é um erro de codificação (pode ser chamado de erro de sintaxe em termos de UTF-8).
Alfe

83

Use esta solução, ela removerá (ignorará) os caracteres e retornará a string sem eles. Use-o somente se for necessário removê-los e não convertê-los.

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

Usando errors='ignore' Você apenas perderá alguns caracteres. mas se você não se importa com eles, eles parecem caracteres extras originários de uma má formatação e programação dos clientes conectados ao meu servidor de soquete. Então é uma solução fácil e direta. referência


6
Obras para decodificar () assim: contents = contents.decode('utf-8', 'ignore')Fonte: docs.python.org/3/howto/unicode.html#the-string-type
naaman

2
Deve ser a melhor resposta
Statham

melhor solução no meu caso de uso :)
maestromusica

Quando você diz "perder alguns caracteres", quer dizer que o arquivo com erros não será lido? ou que nem todo o conteúdo desse arquivo será lido?
10139 msoutopico

@msoutopico Como ele está ignorando os erros, algumas codificações não serão lidas e estão causando problemas. Mas nunca encontrei nenhum conteúdo que foi ignorado durante a leitura. Então, basicamente, os problemas de ecodificação são ignorados.
Nitish Kumar Pal

23

Teve um problema semelhante a este, acabou usando o UTF-16 para decodificar. meu código está abaixo.

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

isso levaria o conteúdo do arquivo como uma importação, mas retornaria o código no formato UTF. dali seria decodificado e separado por linhas.


10
No Python 3, você pode simplificar isso usando o parâmetro de codificaçãowith open(path, encoding='utf-16') as f
Nikolai R Kristiansen

@NikolaiRKristiansen Tentei usar seu método, mas obtive um erro como TypeError: an integer is required (got type str). Por quê? Ambos os arquivos são binários e lidos como rb.
Bogotá

1
@ Bogota O encodingparâmetro só faz sentido ao ler texto. Solte o 'b' do argumento mode e tente novamente. Leia mais nos documentos: docs.python.org/3/library/functions.html#open
Nikolai R Kristiansen


15

Eu me deparei com esse segmento quando sofria o mesmo erro, depois de fazer algumas pesquisas, posso confirmar, este é um erro que ocorre quando você tenta decodificar um arquivo UTF-16 com UTF-8.

Com UTF-16, o primeiro caráter (2 bytes em UTF-16) é uma BOM (Byte Order Mark) , usada como dica de decodificação e não aparece como um caractere na string decodificada. Isso significa que o primeiro byte será FE ou FF e o segundo, o outro.

Pesadamente editado depois que eu descobri a resposta real


Isso terminou 2 horas de dor de cabeça! Abrir o arquivo com open ('filename', 'r') como f: e depois imprimir seu conteúdo mostra UTF-8, que está incorreto.
Nulldroid

4

usarem apenas

base64.b64decode(a) 

ao invés de

base64.b64decode(a).decode('utf-8')

2
está funcionando, mas apenas para entender você pode explicar por que, por favor? :)
Ido Bleicher

3

Se você estiver em um mac, verifique se há um arquivo oculto, .DS_Store. Depois de remover o arquivo, meu programa funcionou.


1

Verifique o caminho do arquivo a ser lido. Meu código continuou me dando erros até eu alterar o nome do caminho para apresentar o diretório de trabalho. O erro foi:

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

1

se você estiver recebendo dados de uma porta serial, verifique se está usando a taxa de transmissão correta (e as outras configurações): decodificando usando ( utf-8 ), mas a configuração errada gerará o mesmo erro

UnicodeDecodeError: o codec 'utf-8' não pode decodificar o byte 0xff na posição 0: byte inicial inválido

para verificar sua configuração de porta serial no Linux: stty -F /dev/ttyUSBX -a


1

Significa simplesmente que alguém escolheu a codificação errada para ler o arquivo.

No Mac, use file -I file.txtpara encontrar a codificação correta. No Linux, use file -i file.txt.


0

Eu tenho o mesmo problema ao processar um arquivo gerado no Linux. Acontece que estava relacionado a arquivos contendo pontos de interrogação.


-1

Eu tive um problema parecido.

Resolvido por:

import io

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

No entanto, eu tive outro problema. Alguns arquivos html (no meu caso) não eram utf-8, então recebi um erro semelhante. Quando excluí esses arquivos html, tudo funcionava sem problemas.

Portanto, exceto ao corrigir o código, verifique também os arquivos dos quais você está lendo, talvez haja uma incompatibilidade de fato.


-4

Se possível, abra o arquivo em um editor de texto e tente alterar a codificação para UTF-8. Caso contrário, faça-o programaticamente no nível do SO.


-4

Eu tenho um problema similar. Eu tento executar um exemplo em tensorflow / models / aim_detection e recebi a mesma mensagem. Tente mudar Python3 para Python2

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.