Python的upper()方法的奇怪行为

时间:2019-07-24 20:06:28

标签: python unicode python-3.7 uppercase

当我偶然发现一个奇怪的结果时,我正在使用一个包含str.upper()和str.lower()函数的Python脚本。当我将字母(带有达西亚语和prosgegrammeni的大写字母,U + 1F89)传递给upper()函数时,结果为ἉΙ,而不是预期的。 / p>

要复制的代码:

print('ᾉ'.upper())

打印

ἉΙ

这是预期的行为还是某种错误?

编辑:我用正确的字符替换了。

2 个答案:

答案 0 :(得分:5)

检查符号(例如,使用this online tool)会告诉您您有一个U+1F89 GREEK CAPITAL LETTER ALPHA WITH DASIA AND YPROSGEGRAMMENI(不是U + 1F88)。

查找该术语,我们在iota subscripts上获得了Wikipedia文章:

  

在仅大写字母的环境中,它再次被表示为稍微减小的iota(小于常规的小写字母的iota)或全尺寸的大写字母的Iota。

您需要一个具有古希腊知识的人来验证这一点,但是乍一看,结果在逻辑上与您最初的想法相同。


现在,仔细阅读Unicode标准的第3.13节发现,您所拥有的符号实际上是作为例外而明确提及的:

  

在D145中折叠案例之前调用规范分解(NFD标准化)是为了捕获非常少见的边缘案例。折叠之前不需要规范化,除了字符U + 0345将希腊字母ypogegrammeni以及将其作为规范分解的一部分的任何字符组合在一起外,例如U+1FC3 greek small letter eta with ypogegrammeni

此外,根据Wikipedia,

  

为了在全大写(“大写”)中使用,Unicode还规定了一种特殊的大小写映射规则,根据该规则,小写字母应映射到大写字母和大写iota的组合(ᾳ→AΙ)。此规则不仅将单音的表示替换为双音的表示,而且还破坏了数字环境中任何大写字母的可逆性,因为大写字母和大写字母iota的组合通常会转换回小写字母和小写字母iota

显然,您在Unicode标准中遇到了一个奇怪的情况,所以这是可以预期的,而不是Python的str.upper()中的错误。

答案 1 :(得分:0)

不是答案,但这可以是错误吗?相同的东西在Python2中可以完美地工作。

Python 2.7.15rc1 (default, Nov 12 2018, 14:31:15)
[GCC 7.3.0] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> print("ᾉ".upper())
ᾉ

Python 3

Python 3.6.7 (default, Oct 22 2018, 11:32:17)
[GCC 8.2.0] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> print("ᾉ".upper())
ἉΙ

Python 3 documentation说,在Unicode标准的3.13节中描述了所使用的大写算法。

我找不到与python 2中使用的信息相同的信息。