UnicodeEncodeError: кодек ascii не может кодировать символ u '\ xef' в позиции 0: порядковый номер не в диапазоне (128)
Я хочу проанализировать свой XML-документ. Поэтому я сохранил свой XML-документ ниже
class XMLdocs(db.Expando):
id = db.IntegerProperty()
name=db.StringProperty()
content=db.BlobProperty()
Теперь мой ниже мой код
parser = make_parser()
curHandler = BasketBallHandler()
parser.setContentHandler(curHandler)
for q in XMLdocs.all():
parser.parse(StringIO.StringIO(q.content))
Я становлюсь ниже ошибки
'ascii' codec can't encode character u'\xef' in position 0: ordinal not in range(128)
Traceback (most recent call last):
File "/base/python_runtime/python_lib/versions/1/google/appengine/ext/webapp/__init__.py", line 517, in __call__
handler.post(*groups)
File "/base/data/home/apps/parsepython/1.348669006354245654/mapreduce/base_handler.py", line 59, in post
self.handle()
File "/base/data/home/apps/parsepython/1.348669006354245654/mapreduce/handlers.py", line 168, in handle
scan_aborted = not self.process_entity(entity, ctx)
File "/base/data/home/apps/parsepython/1.348669006354245654/mapreduce/handlers.py", line 233, in process_entity
handler(entity)
File "/base/data/home/apps/parsepython/1.348669006354245654/parseXML.py", line 71, in process
parser.parse(StringIO.StringIO(q.content))
File "/base/python_runtime/python_dist/lib/python2.5/xml/sax/expatreader.py", line 107, in parse
xmlreader.IncrementalParser.parse(self, source)
File "/base/python_runtime/python_dist/lib/python2.5/xml/sax/xmlreader.py", line 123, in parse
self.feed(buffer)
File "/base/python_runtime/python_dist/lib/python2.5/xml/sax/expatreader.py", line 207, in feed
self._parser.Parse(data, isFinal)
File "/base/data/home/apps/parsepython/1.348669006354245654/parseXML.py", line 136, in characters
print ch
UnicodeEncodeError: 'ascii' codec can't encode character u'\xef' in position 0: ordinal not in range(128)
Ответы
Ответ 1
Кажется, вы попадаете в символ байта UTF-8 (BOM). Попробуйте использовать эту строку unicode с извлеченной спецификацией:
import codecs
content = unicode(q.content.strip(codecs.BOM_UTF8), 'utf-8')
parser.parse(StringIO.StringIO(content))
Я использовал strip
вместо lstrip
, потому что в вашем случае у вас было несколько вхождений спецификации, возможно из-за конкатенированного содержимого файла.
Ответ 2
Фактический лучший ответ для этой проблемы зависит от вашей среды, в частности от того, какую кодировку ожидает ваш терминал.
Самое быстрое однострочное решение - это кодировать все, что вы печатаете, в ASCII, который ваш терминал почти наверняка принимает, при отбрасывании символов, которые вы не можете распечатать:
print ch #fails
print ch.encode('ascii', 'ignore')
Лучшее решение - изменить кодировку терминала на utf-8 и кодировать все как utf-8 перед печатью. Вы должны привыкнуть думать о кодировке Unicode КАЖДЫЙ раз, когда вы печатаете или читаете строку.
Ответ 3
Просто размещение .encode('utf-8')
в конце объекта будет выполнять задание в последних версиях Python.
Ответ 4
Это сработало для меня:
from django.utils.encoding import smart_str
content = smart_str(content)
Ответ 5
Проблема в соответствии с вашей трассировкой - это оператор print
в строке 136 parseXML.py
. К сожалению, вы не посчитали нужным опубликовать эту часть своего кода, но я собираюсь угадать, что это просто для отладки. Если вы измените его на:
print repr(ch)
то вы должны хотя бы увидеть, что вы пытаетесь напечатать.
Ответ 6
Проблема заключается в том, что вы пытаетесь напечатать символ юникода на возможно не-unicode-терминале. Вам необходимо закодировать его с помощью параметра 'replace
перед его печатью, например. print ch.encode(sys.stdout.encoding, 'replace')
.
Ответ 7
Простым решением этой проблемы является установка кодировки по умолчанию для utf8. Следуйте примеру
import sys
reload(sys)
sys.setdefaultencoding('utf8')