lxml обнаружение кодировки слабое .
Однако учтите, что наиболее распространенной проблемой веб-страниц является отсутствие
из (или наличие неправильных) объявлений кодирования. это
поэтому часто достаточно использовать только обнаружение кодирования
BeautifulSoup, называемый UnicodeDammit, а остальное оставить для lxml
собственный HTML-парсер, который работает в несколько раз быстрее.
Я рекомендую обнаруживать кодировку, используя UnicodeDammit , и анализировать, используя lxml .
Кроме того, вы можете использовать заголовок http Content-Type (вам нужно извлечь charset = ENCODING_NAME ) для более точного определения кодировки.
Для этого примера я использую BeautifulSoup4 (также вам нужно установить chardet для лучшего автоопределения, потому что UnicodeDammit использует chardet внутри ):
from bs4 import UnicodeDammit
if http_charset == "":
ud = UnicodeDammit(content, is_html=True)
else:
ud = UnicodeDammit(content, override_encodings=[http_charset], is_html=True)
root = lxml.html.fromstring(ud.unicode_markup)
ИЛИ, чтобы сделать предыдущий ответ более полным, вы можете изменить его на:
if ud.original_encoding != 'utf-8':
content = content.decode(ud.original_encoding, 'replace').encode('utf-8')
Почему это лучше, чем просто использовать chardet?
Вы не игнорируете Content-Type HTTP header
Content-Type: Текст / html; кодировка = UTF-8
Вы не игнорируете метатег http-эквивалент . Пример:
... http-equ = "Content-Type" content = "text / html; charset = UTF-8" ...
Кроме того, вы используете мощность chardet , cjkcodecs и iconvcodec кодеков и и многих других .