我有这个问题试图使用lxml获取HTML文档中的所有文本节点但我得到一个UnicodeEncodeError:'ascii' codec can't encode character u'\xe9' in position 8995: ordinal not in range(128)
。但是,当我尝试找出此页面的编码类型(encoding = chardet.detect(response)['encoding']
)时,它会说utf-8
。单个页面有utf-8和ascii似乎很奇怪。实际上,这个:
fromstring(response).text_content().encode('ascii', 'replace')
解决了这个问题。
这是我的代码:
from lxml.html import fromstring
import urllib2
import chardet
request = urllib2.Request(my_url)
request.add_header('User-Agent',
'Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.0)')
request.add_header("Accept-Language", "en-us")
response = urllib2.urlopen(request).read()
print encoding
print fromstring(response).text_content()
输出:
utf-8
UnicodeEncodeError: 'ascii' codec can't encode character u'\xe9' in position 8995: ordinal not in range(128)
我该怎么做才能解决这个问题?请记住,我想在其他几个页面上执行此操作,因此我不想单独编码。
更新
也许还有其他事情发生在这里。当我在终端上运行这个脚本时,我得到一个正确的输出但是当在SublimeText中运行它时,我得到UnicodeEncodeError ...¿?
UPDATE2:
当我使用此输出创建文件时也会发生这种情况。 .encode('ascii', 'replace')
正在运作,但我希望有一个更通用的解决方案。
此致
答案 0 :(得分:5)
你能尝试用repr()包装你的字符串吗? This article可能有帮助。
print repr(fromstring(response).text_content())
答案 1 :(得分:3)
至于在编辑中写到文件时,我建议使用编解码器模块打开文件:
import codecs
output_file = codecs.open('filename.txt','w','utf8')
我不知道SublimeText,但它似乎试图将您的输出读取为ASCII,因此编码错误。
答案 2 :(得分:0)
基于你的第一次更新,我会说终端告诉Python输出utf-8和SublimeText明确表示它希望ascii。所以我认为解决方案是在SublimeText中找到正确的设置。
但是,如果您无法更改SublimeText所期望的内容,则最好使用encode
函数,就像您在单独的函数中所做的那样。
def smartprint( text ) :
if sys.stdout.encoding == None :
print text
else :
print text.encode( sys.stdout.encoding , 'replace' )
您可以使用此功能代替print
。请记住,在SublimeText中运行时程序的输出与终端不同。由于replace
重音符号在SublimeText中运行此代码时会松开其重音符号,例如é
将显示为e
。