读取UTF8编码的CSV并转换为UTF-16

时间:2013-08-28 11:13:07

标签: python csv unicode encoding utf-8

我正在读取具有UTF8编码的CSV文件:

ifile = open(fname, "r")
for row in csv.reader(ifile):
    name = row[0]
    print repr(row[0])

这很好用,打印出我希望打印出来的内容; UTF8编码str

> '\xc3\x81lvaro Salazar'
> '\xc3\x89lodie Yung'
...

此外,当我只打印str(而不是repr())时,输出显示正常(我不明白 - 这不应该导致错误吗?):

> Álvaro Salazar
> Élodie Yung

但是当我尝试将我的UTF8编码strs转换为unicode时:

ifile = open(fname, "r")
for row in csv.reader(ifile):
    name = row[0]
    print unicode(name, 'utf-8')  # or name.decode('utf-8')

我臭名昭着:

Traceback (most recent call last):                                       
File "scripts/script.py", line 33, in <module>
    print unicode(fullname, 'utf-8')
UnicodeEncodeError: 'ascii' codec can't encode character u'\xc1' in position 0: ordinal not in range(128)

所以我查看了创建的unicode字符串:

ifile = open(fname, "r")
for row in csv.reader(ifile):
    name = row[0]
    unicode_name = unicode(name, 'utf-8')
    print repr(unicode_name)

,输出

 > u'\xc1lvaro Salazar'
 > u'\xc9lodie Yung'

所以现在我完全感到困惑,因为这些似乎是错误的十六进制值。我读过这个问题:

看起来我正在做的一切正确,让我相信我的文件实际上不是UTF8,但是当我最初打印出单元格的repr值时,它们似乎会纠正UTF8十六进制值。任何人都可以指出我的问题或指出我的理解在哪里崩溃(因为我开始迷失在编码的丛林中)


顺便说一句,我相信我可以使用codecs打开文件并直接将其读取到unicode对象中,但csv模块本身不支持unicode,因此我可以使用此方法。

1 个答案:

答案 0 :(得分:5)

您的默认编码是ASCII。当您尝试打印unicode对象时,解释器会尝试使用ASCII编解码器对其进行编码,但由于您的文本包含ASCII中不存在的字符,因此编解码失败。

打印UTF-8编码的字节串不会产生错误(这似乎让您感到困惑,尽管它不应该)的原因是这只是将字节发送到您的终端。它永远不会产生Python错误,但如果你的终端不知道如何处理字节,它可能会产生难看的输出。

要打印unicode,请使用print some_unicode.encode('utf-8')。 (或者您的终端实际使用的任何编码)。

对于u'\xc1lvaro Salazar',此处没有任何内容被破坏。字符Á位于unicode代码点C1(与UTF-8表示无关,但恰好与Latin-1中的值相同),Python使用\x十六进制转义符对于将00作为节省空间的最重要字节的代码点而不是\u unicode代码点表示法(它也可以将其显示为\u00c1。)

为了更好地概述Unicode在Python中的工作原理,我建议http://nedbatchelder.com/text/unipain.html