UnicodeEncodeError: o codec 'charmap' não pode codificar caracteres


205

Estou tentando raspar um site, mas isso gera um erro.

Estou usando o seguinte código:

import urllib.request
from bs4 import BeautifulSoup

get = urllib.request.urlopen("https://www.website.com/")
html = get.read()

soup = BeautifulSoup(html)

print(soup)

E estou recebendo o seguinte erro:

File "C:\Python34\lib\encodings\cp1252.py", line 19, in encode
    return codecs.charmap_encode(input,self.errors,encoding_table)[0]
UnicodeEncodeError: 'charmap' codec can't encode characters in position 70924-70950: character maps to <undefined>

Oque posso fazer para consertar isso?

Respostas:


258

Eu estava recebendo o mesmo UnicodeEncodeErrorao salvar o conteúdo da Web raspado em um arquivo. Para corrigi-lo, substituí este código:

with open(fname, "w") as f:
    f.write(html)

com isso:

import io
with io.open(fname, "w", encoding="utf-8") as f:
    f.write(html)

Usar iofornece compatibilidade retroativa com o Python 2.

Se você precisar apenas suportar o Python 3, poderá usar a openfunção embutida:

with open(fname, "w", encoding="utf-8") as f:
    f.write(html)

6
No mac (python 3) funciona perfeitamente com apenas abrir sem codificação, mas no windows (w10, python3) não é uma opção. Apenas funciona dessa maneira, com o parâmetro encoding = "utf-8".
precisa saber é o seguinte

3
Obrigado. Ela trabalhou para mim, eu estava trabalhando com arquivos XML e escrever o resultado de xml.toprettyxml () em um novo arquivo
Luis Cabrera Benito

1
Essa deve ser a resposta aceita, pois acabará gravando uma string na saída, e não uma representação de bytes.
Shirkan 14/02/19

O OP solicitou a leitura do arquivo, no entanto, não o gravou. O problema parece estar relacionado ao console.
NaturalBornCamper 20/09/19

187

Corrigi-o adicionando .encode("utf-8")a soup.

Isso significa que print(soup)se torna print(soup.encode("utf-8")).


3
não codificar a codificação de caracteres do seu ambiente (por exemplo, console) dentro do seu roteiro, imprimir Unicode diretamente em vez
JFS

Isso é apenas imprimir o repr de um bytesobjeto, que será impresso como uma bagunça de \xsequências, se houver muito texto codificado em UTF-8. Eu recomendo usar win_unicode_console, como sugere o @JFSebastian.
Eryk Sun

2
Eu usei a solução acima, mas ainda estou tendo problemas: classe MyStreamListener (tweepy.StreamListener): def on_status (self, status): print (str (status.encode ("utf-8")))) UnicodeEncodeError: 'charmap' codec can ' t codifica o caractere '\ u2019' na posição 87: mapas de caracteres para <indefinido> #
264 Vivek

2
Isso torna imprimir b'\x02x\xc2\xa9'(um objeto bytes) em vez
MilkyWay90

1
print(soup.encode("utf-8"))trabalhou para mim, mas antes que eu tive que também adicionarwith open("f_name", encoding="utf-8") as f: soup = BeautifulSoup(f, "html.parser")
TheWalkingData

44

No Python 3.7, e executando o Windows 10, isso funcionou (não tenho certeza se ele funcionará em outras plataformas e / ou outras versões do Python)

Substituindo esta linha:

with open('filename', 'w') as f:

Com isso:

with open('filename', 'w', encoding='utf-8') as f:

A razão pela qual está funcionando é porque a codificação é alterada para UTF-8 ao usar o arquivo, para que os caracteres em UTF-8 possam ser convertidos em texto, em vez de retornar um erro quando encontrar um caractere UTF-8 que é não suporta a codificação atual.


1
print (sopa) return \ xd0 \ xbf \ xd0 \ xbe \ xd0 \ xb6 \ xd0 \ xb0 \ xd0 \ xbb \ xd1 \ x83 \ xd0 \ xb9 \ xd
Coffee inTime

12

Ao salvar a resposta da solicitação de obtenção, o mesmo erro foi lançado no Python 3.7 na janela 10. A resposta recebida da URL, a codificação foi UTF-8, portanto, é sempre recomendável verificar a codificação para que a mesma possa ser passada para evitar esse problema trivial pois realmente mata muito tempo na produção

import requests
resp = requests.get('https://en.wikipedia.org/wiki/NIFTY_50')
print(resp.encoding)
with open ('NiftyList.txt', 'w') as f:
    f.write(resp.text)

Quando adicionei encoding = "utf-8" ao comando open, ele salvou o arquivo com a resposta correta

with open ('NiftyList.txt', 'w', encoding="utf-8") as f:
    f.write(resp.text)

10

Até eu enfrentei o mesmo problema com a codificação que ocorre quando você tenta imprimi-lo, lê / escreve ou abre. Como outros mencionados acima, adicionar .encoding = "utf-8" ajudará se você estiver tentando imprimi-lo.

soup.encode ("utf-8")

Se você estiver tentando abrir dados raspados e talvez gravá-los em um arquivo, abra o arquivo com (......, encoding = "utf-8")

com open (filename_csv, 'w', newline = '', encoding = "utf-8") como csv_file:


6

Para aqueles que ainda estão recebendo esse erro, adicionar encode("utf-8")ao souptambém corrigirá isso.

soup = BeautifulSoup(html_doc, 'html.parser').encode("utf-8")
print(soup)

2
soupnão é mais um BeautifulSoupobjeto depois de fazer isso de modo que não pode ser manipulado ou procurou
NaturalBornCamper
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.