什么时候`string.swapcase().swapcase()` 不等于`string`?

el *_*gli 4 python string character character-encoding python-3.x

str.swapcase() 方法的文档说:

返回字符串的副本,其中大写字符转换为小写,反之亦然。请注意, s.swapcase().swapcase() == s 不一定正确

我想不出一个例子s.swapcase().swapcase() != s,谁能想到一个?

ruo*_*ola 5

一个简单的例子是:

s = "ß"

print(s.swapcase().swapcase())
Run Code Online (Sandbox Code Playgroud)

输出:

s = "ß"

print(s.swapcase().swapcase())
Run Code Online (Sandbox Code Playgroud)

ß是德语小写 double s(正确的大写版本是?)。发生这种情况的原因是 Python 不“知道”或不想为每个单个 unicode 符号定义大写转换。所以它通过评估s.swapcase()as采取了简单的路线"SS",因此s.swapcase().swapcase()也是"ss"

  • “ß”到“ss”的映射由 Unicode 联盟定义 - 请参阅 ftp://ftp.unicode.org/Public/UCD/latest/ucd/SpecialCasing.txt。Python 并不“了解”或“决定”任何事情,它只是实现标准。Python 在每个版本中捆绑了 Unicode 数据库的副本,并在该数据库中查找字符信息;Python 不会对大小写映射等做出独立决定。 (2认同)

sen*_*nce 5

事实上,有很多例子:它发生在一些希腊符号、德语符号、亚美尼亚符号和其他特定/特殊符号上。

\n\n

要获得全部:

\n\n
find_dif = lambda s: s.swapcase().swapcase() != s\n\n[chr(s) for s in range(100000) if find_dif(chr(s))]\n
Run Code Online (Sandbox Code Playgroud)\n\n

你得到:

\n\n
\n

[\'\xc2\xb5\',\n \'\xc3\x9f\',\n \'\xc4\xb0\',\n \'\xc4\xb1\',\n \'\xc5\ x89\',\n \'\xc5\xbf\',\n \'\xc7\xb0\',\n \'\xcd\x85\',\n \'\xce\x90\',\n \'\xce\xb0\'、\n \'\xcf\x82\'、\n \'\xcf\x90\'、\n \'\xcf\x91\'、\n \'\xcf\x95 \'、\n \'\xcf\x96\'、\n \'\xcf\xb0\'、\n \'\xcf\xb1\'、\n \'\xcf\xb4\'、\n \ '\xcf\xb5\',\n \'\xd6\x87\',\n \'\xe1\xb2\x80\',\n \'\xe1\xb2\x81\',\n \'\ xe1\xb2\x82\',\n \'\xe1\xb2\x83\',\n \'\xe1\xb2\x84\',\n \'\xe1\xb2\x85\',\n \ '\xe1\xb2\x86\',\n \'\xe1\xb2\x87\',\n \'\xe1\xb2\x88\',\n \'\xe1\xba\x96\',\ n \'\xe1\xba\x97\',\n \'\xe1\xba\x98\',\n \'\xe1\xba\x99\',\n \'\xe1\xba\x9a\' ,\n \'\xe1\xba\x9b\',\n \'\xe1\xba\x9e\',\n \'\xe1\xbd\x90\',\n \'\xe1\xbd\x92 \',\n \'\xe1\xbd\x94\',\n \'\xe1\xbd\x96\',\n \'\xe1\xbe\x80\',\n \'\xe1\xbe \x81\'、\n \'\xe1\xbe\x82\'、\n \'\xe1\xbe\x83\'、\n \'\xe1\xbe\x84\'、\n \'\xe1 \xbe\x85\'、\n \'\xe1\xbe\x86\'、\n \'\xe1\xbe\x87\'、\n \'\xe1\xbe\x90\'、\n \' \xe1\xbe\x91\',\n \'\xe1\xbe\x92\',\n \'\xe1\xbe\x93\',\n \'\xe1\xbe\x94\',\n \'\xe1\xbe\x95\',\n \'\xe1\xbe\x96\',\n \'\xe1\xbe\x97\',\n \'\xe1\xbe\xa0\', \n \'\xe1\xbe\xa1\'、\n \'\xe1\xbe\xa2\'、\n \'\xe1\xbe\xa3\'、\n \'\xe1\xbe\xa4\ ',\n \'\xe1\xbe\xa5\',\n \'\xe1\xbe\xa6\',\n \'\xe1\xbe\xa7\',\n \'\xe1\xbe\ xb2\',\n \'\xe1\xbe\xb3\',\n \'\xe1\xbe\xb4\',\n \'\xe1\xbe\xb6\',\n \'\xe1\ xbe\xb7\',\n \'\xe1\xbe\xbe\',\n \'\xe1\xbf\x82\',\n \'\xe1\xbf\x83\',\n \'\ xe1\xbf\x84\',\n \'\xe1\xbf\x86\',\n \'\xe1\xbf\x87\',\n \'\xe1\xbf\x92\',\n \ '\xe1\xbf\x93\',\n \'\xe1\xbf\x96\',\n \'\xe1\xbf\x97\',\n \'\xe1\xbf\xa2\',\ n \'\xe1\xbf\xa3\',\n \'\xe1\xbf\xa4\',\n \'\xe1\xbf\xa6\',\n \'\xe1\xbf\xa7\' ,\n \'\xe1\xbf\xb2\',\n \'\xe1\xbf\xb3\',\n \'\xe1\xbf\xb4\',\n \'\xe1\xbf\xb6 \',\n \'\xe1\xbf\xb7\',\n \'\xe2\x84\xa6\',\n \'\xe2\x84\xaa\',\n \'\xe2\x84 \xab\',\n \'\xef\xac\x80\',\n \'\xef\xac\x81\',\n \'\xef\xac\x82\',\n \'\xef \xac\x83\'、\n \'\xef\xac\x84\'、\n \'\xef\xac\x85\'、\n \'\xef\xac\x86\'、\n \' \xef\xac\x93\',\n \'\xef\xac\x94\',\n \'\xef\xac\x95\',\n \'\xef\xac\x96\',\n \'\xef\xac\x97\']

\n
\n\n

让我们来看看它们:

\n\n
find_dif = lambda s: s.swapcase().swapcase() != s\n\n[chr(s) for s in range(100000) if find_dif(chr(s))]\n
Run Code Online (Sandbox Code Playgroud)\n\n
\n

错误的

\n
\n\n
s1 = \'\xc2\xb5\'\ns2 = s1.swapcase().swapcase()\n\ns1 == s2\n
Run Code Online (Sandbox Code Playgroud)\n\n
\n

错误的

\n
\n\n
s1 = \'\xef\xac\x97\'\ns2 = s1.swapcase().swapcase()\n\ns1 == s2\n
Run Code Online (Sandbox Code Playgroud)\n\n
\n

错误的

\n
\n