我正在尝试在python生成的PDF中使用á
和ô
等字符。该程序使用dateutil模块(和其他几个)生成PDF日历(带图像)。日历用Latex布局。
我的目标是用法语创建日历,但法语中的月份名称数组包含似乎无法被python识别的字符。
在生成过程中,程序在命令行中打印SyntaxError: (unicode error) 'utf-8' codec can't decode byte 0xe9 in position 0: unexpected end of data
。
如何告诉python使用这些字符?
如果它有助于数组:
FRENCH_MONTHS = [u'NotAMonth', u'Janvier', u'Février', u'Mars', u'Avril', u'Mai', u'Juin', u'Juillet', u'Aôut', u'Septembre', u'Octobre', u'Novembre', u'Décembre']
也用过:
答案 0 :(得分:3)
您必须指定用于创建python源的源代码。通过添加source encoding declaration:
来完成此操作# coding: UTF-8
这应该是python源文件的第一行或第二行。编码具有以匹配您保存文件的编码;检查文本编辑器设置。您添加到问题中的错误消息表明编码不匹配,我怀疑您使用的是latin-1(ISO 8859-1)。
或者,使用unicode转义包含非ASCII字符; u'\u00e9'
表示带有重音坟墓的e作为unicode代码点。
请研究Python如何在Python Unicode HOWTO中处理Unicode。对于任何处理任何非ASCII数据的软件开发人员,Joel Spolsky Unicode article也是必要的读数。
答案 1 :(得分:2)
如果你的编辑器设置为使用正确的编码保存文件,你可以使用# coding: UTF-8
或者,您也可以将字符编码为仅ASCII转义序列。例如,escape-sequence for é
为\u00E9
:
FRENCH_MONTHS = [u'NotAMonth', u'Janvier', u'F\u00E9vrier', ...]
这不太可能被配置错误的编辑器弄乱,但实现完全相同的事情。
更好的是,您可以使用calendar
模块并回避整个问题(基于this answer):
import calendar
def get_month_names(locale):
with calendar.TimeEncoding(locale) as encoding:
months = list(calendar.month_name)
# Could do this to match original values:
# months = [x.title() for x in months]
if encoding is not None:
months = [x.decode(encoding) for x in months]
months[0] = u"NotAMonth"
return months
FRENCH_MONTHS = get_month_names("fr_FR.UTF-8")
编辑:这与this question的问题相同 - 您的é使用latin 1
编码,但您的Python源文件编码是UTF-8(在Python 2中显式设置,或者因为它是Python 3)中的默认值:
>>> print "\xe9".decode("latin1")
é
>>> print "\xe9".decode("utf-8")
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File ".../python2.7/encodings/utf_8.py", line 16, in decode
return codecs.utf_8_decode(input, errors, True)
UnicodeDecodeError: 'utf8' codec can't decode byte 0xe9 in position 0: unexpected end of data
使用上述替代解决方案的另一个好理由!