从Python中的文件读取字符

时间:2008-09-29 06:47:48

标签: python unicode encoding ascii

在文本文件中,有一个字符串“我不喜欢这个”。

然而,当我把它读成一个字符串时,它变成了“我不喜欢这样”。我明白\ u2018是“'”的unicode表示。我用

f1 = open (file1, "r")
text = f1.read()

命令进行阅读。

现在,是否有可能以这样一种方式读取字符串:当它被读入字符串时,它是“我不喜欢这个”,而不是“我不喜欢这样的字符串”这种“?

第二次编辑:我看到有些人使用映射来解决这个问题,但实际上,是否没有内置转换可以将这种ANSI转换为unicode(反之亦然)?

9 个答案:

答案 0 :(得分:142)

参考:http://docs.python.org/howto/unicode

从文件中读取Unicode非常简单:

import codecs
f = codecs.open('unicode.rst', encoding='utf-8')
for line in f:
    print repr(line)

也可以在更新模式下打开文件,允许读写:

f = codecs.open('test', encoding='utf-8', mode='w+')
f.write(u'\u4500 blah blah blah\n')
f.seek(0)
print repr(f.readline()[:1])
f.close()

编辑:我假设您的目标只是能够将文件正确地读入Python中的字符串。如果您尝试从Unicode转换为ASCII字符串,那么实际上没有直接的方法,因为Unicode字符不一定存在于ASCII中。

如果您要尝试转换为ASCII字符串,请尝试以下操作之一:

  1. 如果您只想处理一些特殊情况,例如此特定示例,请使用ASCII等效替换特定的unicode字符

  2. 使用unicodedata模块的normalize()string.encode()方法尽可能地转换为下一个最接近的ASCII等效值(Ref https://web.archive.org/web/20090228203858/http://techxplorer.com/2006/07/18/converting-unicode-to-ascii-using-python):

    >>> teststr
    u'I don\xe2\x80\x98t like this'
    >>> unicodedata.normalize('NFKD', teststr).encode('ascii', 'ignore')
    'I donat like this'
    

答案 1 :(得分:15)

有几点需要考虑。

\ u2018字符可能仅作为Python中unicode字符串表示的片段出现,例如如果你写:

>>> text = u'‘'
>>> print repr(text)
u'\u2018'

现在,如果您只是想要巧妙地打印unicode字符串,只需使用unicode的encode方法:

>>> text = u'I don\u2018t like this'
>>> print text.encode('utf-8')
I don‘t like this

为了确保任何文件中的每一行都被读取为unicode,您最好使用codecs.open函数,而不仅仅是open,这允许您指定文件的编码:

>>> import codecs
>>> f1 = codecs.open(file1, "r", "utf-8")
>>> text = f1.read()
>>> print type(text)
<type 'unicode'>
>>> print text.encode('utf-8')
I don‘t like this

答案 2 :(得分:6)

但它确实是“我不喜欢这样”而不是“我不喜欢这个”。字符u'\ u2018'是一个完全不同于“'”的字符(并且,在视觉上,应该更多地对应于''')。

如果您正在尝试将编码的unicode转换为纯ASCII,您可以保留您想要转换为ASCII的unicode标点符号的映射。

punctuation = {
  u'\u2018': "'",
  u'\u2019': "'",
}
for src, dest in punctuation.iteritems():
  text = text.replace(src, dest)

然而,有很多punctuation characters in unicode,但我认为你可以指望它们中只有少数实际被正在用于创建你正在阅读的文档的应用程序使用。

答案 3 :(得分:3)

不考虑文本文件被破坏的事实(U + 2018是左引号,而不是撇号):iconv可用于将unicode字符音译为ascii。

你必须google for“iconvcodec”,因为该模块似乎不再受支持了,我找不到它的规范主页。

>>> import iconvcodec
>>> from locale import setlocale, LC_ALL
>>> setlocale(LC_ALL, '')
>>> u'\u2018'.encode('ascii//translit')
"'"

或者,您可以使用iconv命令行实用程序来清理文件:

$ xxd foo
0000000: e280 980a                                ....
$ iconv -t 'ascii//translit' foo | xxd
0000000: 270a                                     '.

答案 4 :(得分:2)

有可能你有一个带有unicode转义字符的非unicode字符串,例如:

>>> print repr(text)
'I don\\u2018t like this'

这实际上发生在我之前。您可以使用unicode_escape编解码器将字符串解码为unicode,然后将其编码为您想要的任何格式:

>>> uni = text.decode('unicode_escape')
>>> print type(uni)
<type 'unicode'>
>>> print uni.encode('utf-8')
I don‘t like this

答案 5 :(得分:1)

实际上,U + 2018是特殊字符的Unicode表示。如果需要,可以使用以下代码将该字符的实例转换为U + 0027:

text = text.replace (u"\u2018", "'")

另外,你用什么来写文件? f1.read()应该返回一个如下所示的字符串:

'I don\xe2\x80\x98t like this'

如果它正在返回字符串,则文件写入错误:

'I don\u2018t like this'

答案 6 :(得分:1)

这是Pythons的方式,可以显示unicode编码的字符串。但我认为您应该能够在屏幕上打印字符串或将其写入新文件而没有任何问题。

>>> test = u"I don\u2018t like this"
>>> test
u'I don\u2018t like this'
>>> print test
I don‘t like this

答案 7 :(得分:1)

还可以使用python 3 read方法读取编码的文本文件:

f = open (file.txt, 'r', encoding='utf-8')
text = f.read()
f.close()

有了这种变体,就无需导入任何其他库

答案 8 :(得分:0)

不确定 (errors="ignore") 选项,但它似乎适用于带有奇怪 Unicode 字符的文件。

with open(fName, "rb") as fData:
    lines = fData.read().splitlines()
    lines = [line.decode("utf-8", errors="ignore") for line in lines]