Kat*_*kas 3 python unicode utf-8 utf-16 cjk
网络上有很多关于这个问题的主题,但我似乎无法找到我的具体案例的答案。
我有一个 CSV 文件。我不确定对它做了什么,但是当我尝试打开它时,我得到:
UnicodeDecodeError: 'utf8' 编解码器无法解码位置 0 中的字节 0xff:起始字节无效
这是一个完整的Traceback:
Traceback (most recent call last):
File "keywords.py", line 31, in <module>
main()
File "keywords.py", line 28, in main
get_csv(file_full_path)
File "keywords.py", line 19, in get_csv
for row in reader:
UnicodeEncodeError: 'ascii' codec can't encode character u'\u5a07' in position 10: ordinal not in range(128)
Run Code Online (Sandbox Code Playgroud)
在 Stack Overflow 的帮助下,我打开了它:
reader = csv.reader(codecs.open(file_full_path, 'rU', 'UTF-16'), delimiter='\t', quotechar='"')
现在的问题是,当我读取文件时:
def get_csv(file_full_path):
import csv, codecs
reader = csv.reader(codecs.open(file_full_path, 'rU', 'UTF-16'), delimiter='\t', quotechar='"')
for row in reader:
print row
Run Code Online (Sandbox Code Playgroud)
我被亚洲符号困住了:
UnicodeEncodeError: 'ascii' 编解码器无法对位置 10 中的字符 u'\u5a07' 进行编码:序号不在范围内 (128)
我在包含该字符的字符串上尝试过decode'encode' unicode(),但似乎没有帮助。
for row in reader:
#decoded_row = [element_s.decode('UTF-8') for element_s in row]
#print decoded_row
encoded_row = [element_s.encode('UTF-8') for element_s in row]
print encoded_row
Run Code Online (Sandbox Code Playgroud)
在这一点上我真的不明白为什么。如果我
>>> print u'\u5a07'
?
Run Code Online (Sandbox Code Playgroud)
或者
>>> print '?'
?
Run Code Online (Sandbox Code Playgroud)
有用。同样在终端中,它也可以工作。我检查了终端和 Python shell 上的默认编码,到处都是 UTF-8。它可以轻松打印该符号。我认为这与我codecs使用 UTF-16打开文件有关。
我不知道从这里去哪里。有人可以帮忙吗?
该csv模块无法处理 Unicode 输入。它在其文档页面上特别说明:
注意:此版本的
csv模块不支持 Unicode 输入。此外,目前存在一些关于 ASCII NUL 字符的问题。因此,所有输入都应该是 UTF-8 或可打印的 ASCII 以确保安全;
您需要将 CSV 文件转换为 UTF-8,以便模块可以处理它:
with codecs.open(file_full_path, 'rU', 'UTF-16') as infile:
with open(file_full_path + '.utf8', 'wb') as outfile:
for line in infile:
outfile.write(line.encode('utf8'))
Run Code Online (Sandbox Code Playgroud)
或者,您可以使用命令行实用程序iconv为您转换文件。
然后使用该重新编码的文件来读取您的数据:
reader = csv.reader(open(file_full_path + '.utf8', 'rb'), delimiter='\t', quotechar='"')
for row in reader:
print [c.decode('utf8') for c in row]
Run Code Online (Sandbox Code Playgroud)
请注意,这些列需要手动解码为 unicode。