如何迭代unicode符号,而不是python中的字节?

时间:2013-12-26 12:04:03

标签: python unicode python-unicode

鉴于像u'кни́га'这样的重音单词,我需要删除锐化(u'книга'),并将重音格式更改为u'кни+га',其中'+'代表对前一封信很敏感。

我现在所做的是使用一个有效且无法完成符号的词典:

accented_list = [u'я́', u'и́', u'ы́', u'у́', u'э́', u'а́', u'е́', u'ю́', u'о́']
regular_list = [u'я', u'и', u'ы', u'у', u'э', u'а', u'е',  u'ю', u'о']
accent_dict = dict(zip(accented_list, regular_list))

我想做这样的事情:

def changeAccentFormat(word):
  for letter in accent_dict:
    if letter in word:
      its_index = word.index(letter)
      word = word[:its_index + 1] + u'+' + word[its_index + 1:]
  return word

但当然它不能按预期工作。我注意到这段代码:

>>> word = u'кни́га'
>>> for letter in word:
...     print letter

给出

к
н
и                                                                                                                                                                                  
´   

г
а

(好吧,我没想到会出现空白符号,但仍然如此)。所以我想知道,生成[u'к', u'н', u'и́', u'г', u'а']的最简单方法是什么?或者也许有一些方法可以在没有它的情况下解决我的问题?

3 个答案:

答案 0 :(得分:6)

首先,关于迭代字符而不是字节,你已经做得对了 - 你的word是一个unicode对象,而不是一个编码的字节串。

现在,对于Unicode中的组合字符:

对于包含组合字符的许多字符,有一种组合分解形式的写作,组合为一个代码点,分解为两个序列(或更多?)代码点:

Composed and decomposed form of c with cedilla

请参阅U+00E7U+0063U+0327

所以在Python中,您既可以编写任何一种形式,也可以在显示时将其组合成相同的字符:

>>> combining_cedilla = u'\u0327'
>>> c_with_cedilla = u'\u00e7'
>>> letter_c = u'\u0063'
>>>
>>> print c_with_cedilla
ç
>>> print letter_c + combining_cedilla
ç

为了在撰写和分解的表单之间进行转换,您可以使用unicodedata.normalize()

>>> import unicodedata
>>> comp = unicodedata.normalize('NFC', letter_c + combining_cedilla)
>>> decomp = unicodedata.normalize('NFD', c_with_cedilla)
>>>
>>> print comp
ç
>>> print decomp
ç

NFC代表“普通形式C”(组成),NFD代表“普通形式D”(已分解)。

他们仍然 不同的形式 - 一个由一个代码点组成,另一个包含两个:

>>> comp == decomp
False
>>> len(comp)
1
>>> len(decomp)
2

但是,在你的情况下,似乎没有小写и的组合字符,其中重音是急性的(и with an accent grave有一个)

答案 1 :(得分:1)

Acutes由代码点301 COMBINING ACUTE ACCENT表示,因此简单的字符串替换就足够了:

>>>print u'кни́га'.replace(u'\u0301', "+")
кни+га

如果您遇到未使用组合重音编码的重音字符,unicodedata.normalize应该可以做到这一点

答案 2 :(得分:1)

您可以使用regex模块生成[u'к', u'н', u'и́', u'г', u'а']

以下是每个用户感知角色所拥有的词:

>>> import regex
>>> word = u'кни́га'
>>> len(word)
6
>>> regex.findall(r'\X', word)
['к', 'н', 'и́', 'г', 'а']
>>> len(regex.findall(r'\X', word))
5
相关问题