删除Python unicode字符串中的重音符号(规范化)的最佳方法是什么?

2024-09-30 20:32:40 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个Python中的Unicode字符串,我想删除所有的重音符号(变音符号)

我在web上发现了一种优雅的方法(Java):

  1. 将Unicode字符串转换为其长规范化形式(字母和变音符号使用单独的字符)
  2. 删除Unicode类型为“dicritic”的所有字符

我是否需要安装pyICU之类的库,或者只安装Python标准库就可以了?那么python 3呢

重要提示:我希望避免代码使用从重音字符到非重音字符的显式映射


Tags: 方法字符串web类型字母unicode符号java
3条回答

Unidecode是这方面的正确答案。它将任何unicode字符串转换为ascii文本中最接近的表示形式

例如:

accented_string = u'Málaga'
# accented_string is of type 'unicode'
import unidecode
unaccented_string = unidecode.unidecode(accented_string)
# unaccented_string contains 'Malaga'and is of type 'str'

我刚刚在网上找到了这个答案:

import unicodedata

def remove_accents(input_str):
    nfkd_form = unicodedata.normalize('NFKD', input_str)
    only_ascii = nfkd_form.encode('ASCII', 'ignore')
    return only_ascii

它可以很好地工作(例如法语),但我认为第二步(删除重音)可能比删除非ASCII字符处理得更好,因为对于某些语言(例如希腊语),这将失败。最好的解决方案可能是显式删除标记为变音符号的unicode字符

编辑:这样做可以:

import unicodedata

def remove_accents(input_str):
    nfkd_form = unicodedata.normalize('NFKD', input_str)
    return u"".join([c for c in nfkd_form if not unicodedata.combining(c)])

如果字符unicodedata.combining(c)可以与前面的字符组合,则c将返回true,这主要是在它是变音符号的情况下

编辑2remove_accents需要的是unicode字符串,而不是字节字符串。如果有字节字符串,则必须将其解码为unicode字符串,如下所示:

encoding = "utf-8" # or iso-8859-15, or cp1252, or whatever encoding you use
byte_string = b"café"  # or simply "café" before python 3.
unicode_string = byte_string.decode(encoding)

这个怎么样:

import unicodedata
def strip_accents(s):
   return ''.join(c for c in unicodedata.normalize('NFD', s)
                  if unicodedata.category(c) != 'Mn')

这也适用于希腊字母:

>>> strip_accents(u"A \u00c0 \u0394 \u038E")
u'A A \u0394 \u03a5'
>>> 

character category“Mn”代表Nonspacing_Mark,类似于MiniQuark答案中的unicodedata.combing(我没有想到unicodedata.combing,但它可能是更好的解决方案,因为它更明确)

请记住,这些操作可能会显著改变文本的含义。口音、口音等不是“装饰”

相关问题 更多 >