删除奇怪的 ANSI 字符并使用 Python 转换重音字符

Delete weird ANSI character and convert accented ones using Python

我已经使用 Twitter API 下载了一堆西班牙语推文,但其中一些包含我不想要的奇怪的 ANSI 字符。我有大约 18000 个文件,我想删除这些字符。我将所有文件编码为 UTF-8。 例如:

b'Me quedo con una frase de nuestra reuni\xc3\xb3n de hoy.'

如果它们是重音字符(我们有很多西班牙语),我想删除重音字母并将其替换为它的非重音版本。那是因为在那之后我正在做一些文本挖掘分析,我想统一这些词,因为可能有人不使用重音。 我认为 b 的意思是字节模式。

在之前的情况下,如果我将以下内容放入 python:

print(u'Me quedo con una frase de nuestra reuni\xc3\xb3n de hoy con @Colegas')

我在终端中得到了这个:

Me quedo con una frase de nuestra reunión de hoy con @Colegas

我不喜欢,因为它不是西班牙语中的常用口音。应该有字符 ó。我不明白为什么也不正确。 我还希望文件开头的 b 消失。 为了对文件进行编码,我使用了以下内容:

f.write(str(FILE.encode('utf-8','strict')))

我用一些 json 格式的 UTF-8 创建我的文件,其中包含每条推文的大量密钥。也许我应该改变它或者我在那里做错了。

在某些情况下,尝试获取 python 终端中的字符时也会出现问题。例如:

print(u'\uD83D\uDC1F')

我认为那是因为 python 不能代表那些字符(在上面的例子中)。是这样吗?我也想删除它们。

抱歉,如果有一些英文错误,请随时询问是否不清楚。

提前致谢。

编辑:我正在使用 Python 3.4

首先:您需要 100% 确定这些字符在 Twitter 中使用何种语言编码。如果您确定它是 ANSI(通常西班牙语编码语言将是 Latin-1),那么您从 twitter 获得的所有内容都需要使用此功能

a = getStufFromTwitter() #you parse twitter 
myStr = a.encode('Latin-1') 

.encode('ANSI') 会告诉 python 你从外面拿走的所有东西都是用 ANSI 写的,他应该把它转换成 Unicode。

然后,每当您想在程序的任何部分重新使用 myStr 时(特别是如果您想将它写在某个地方),您都必须使用 decode 函数。在你的情况下是:

with open('myfile.txt','w') as f:
    f.write(myStr.decode('UTF-8'))

这应该有效。但是,如果我们能看到大部分代码,那么帮助您会更容易。您在 Python 中有一些非常恶毒的规范(您使用的是 Python 2.7 吗?如果是,请在每个脚本的开头添加以下内容:

from __future__ import unicode_literals 

再一次,这是python的一个非常棘手的部分。

您正在混合苹果和橙子。 b'reuni\xc3\xb3n'u'reuni\u00f3n' 的 UTF-8 编码,当然是 reunión 人类可读格式。

>>> print b'reuni\xc3\xb3n'.decode('utf-8')
reunión
>>> repr(b'reuni\xc3\xb3n'.decode('utf-8'))
"u'reuni\xf3n'"

这里没有 "ANSI"(无论如何这是用词不当;通常用于指代 Windows 字符编码,但不一定是您期望的那种)。

至于如何从重音字符中删除重音,简短版本是标准化为 Unicode "NFD" 表示,然后丢弃任何具有 "diacritic" 分类的代码点。这包括例如在 What is the best way to remove accents in a Python unicode string? 中;为了使这个答案独立,这里是该问题的一个答案的要点——但请阅读所有这些答案,如果只是为了决定哪个最适合您的用例。

import unicodedata
stripped = u"".join([c for c in unicodedata.normalize('NFKD', input_str)
    if not unicodedata.combining(c)])

Python3 中处理传入文本(bytes 形式)的模式之一是在收到时立即解码。

所以你从推特上得到;

In [1]: tweetbytes = b'Me quedo con una frase de nuestra reuni\xc3\xb3n de hoy.'

而你做到了;

In [2]: tweet = tweetbytes.decode('utf-8')

记住首字母缩略词 BADTIE;字节被解码,文本被编码。

现在是文字;

In [3]: type(tweet)
Out[3]: str

您可以这样使用它;

In [4]: print(tweet)
Me quedo con una frase de nuestra reunión de hoy.