已编辑。我正在使用带有lxml的BeautifulSoup来解析来自外部源的XML文档。奇怪的是,在一些文档中,解析器似乎放弃了文本的中间并缩短了文档。
我已将其缩减为精确的测试用例:
from bs4 import BeautifulSoup
xml = "<ElementA><ElementB>Before bad character XX\n\x80 BAD\nAfter bad character</ElementB><ElementC>In element C</ElementC></ElementA>"
soup = BeautifulSoup(xml,"xml")
soup
输出错误:
<?xml version="1.0" encoding="utf-8"?>
<ElementA><ElementB/></ElementA>
但是,如果我改变一件事并删除一个字符&#39; X&#39;:
from bs4 import BeautifulSoup
xml = "<ElementA><ElementB>Before bad character X\n\x80 BAD\nAfter bad character</ElementB><ElementC>In element C</ElementC></ElementA>"
soup = BeautifulSoup(xml,"xml")
soup
然后我得到更完整的输出:
<?xml version="1.0" encoding="utf-8"?>
<ElementA><ElementB>Before bad character X
BAD
After bad character</ElementB><ElementC>In element C</ElementC></ElementA>
发生了什么事?我在Python 3.4.3,OSX上使用BeautifulSoup 4.3.2和LXML 3.4.4。
到目前为止,我已经设法通过在解析之前将XML字符串传递给UnicodeDammit.detwingle()
来解决这个问题,但如果我能理解发生了什么以及一个附加角色可以拥有什么,我会更放心。对文件造成这种破坏性影响。
修改。使用detwingle
或ftfy
等工具不再有效。这是一个替代测试用例,具有正确的编码,在我的机器上没有被bs4 / lxml正确解析:
xml = "<ElementA><ElementB>Before bad character XX\n• BAD\nAfter bad character</ElementB><ElementC>In element C</ElementC></ElementA>"
如上所述发生同样的问题。 谁能解释一下?
答案 0 :(得分:1)
这可能不是最佳解决方案,但这是我在抓取非ascii网站时所做的。它每次都很完美。
将默认编码更改为与网站相同的编码。在您的情况下utf-8
import sys
reload(sys)
sys.setdefaultencoding('utf-8')
所以打印/保存或解析你刚才做的任何非ascii字符,
print 'non-ascii character'.encode('utf-8','ignore') # Replace your text or variable instead of 'non-ascii character'
希望有所帮助