<pre><code>>>> import re
>>> name = "Test with-name and_underscore"
>>> print(''.join(x.capitalize() for x in re.compile(r'[^a-zA-Z0-9]').split(name)))
TestWithNameAndUnderscore
</code></pre>
<p>如果需要的话,你也可以去掉前导数字。下面是一个更加健壮的示例,它可以做到这一点并确保生成的字符串不是空的:</p>
<pre><code>>>> import re
>>> def fix_id(s, split=re.compile('[^a-zA-Z0-9]+|^[0-9]+').split):
... result = ''.join(x.capitalize() for x in split(s))
... if not result:
... raise ValueError('Invalid ID (empty after edits)')
... return result
...
>>> fix_id("Test with-name and_underscore")
'TestWithNameAndUnderscore'
>>> fix_id("123 Test 456 with-name and_underscore 789")
'Test456WithNameAndUnderscore789'
>>> fix_id("Thisshouldbeunmolested")
'Thisshouldbeunmolested'
>>> fix_id('123')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 4, in fix_id
ValueError: Invalid ID (empty after edits)
</code></pre>
<p>请注意,这两者都不能保证标识符的唯一性,例如,“Mary Sue”和“Mary Sue”将映射到同一标识符。如果需要将这些映射到不同的标识符,可以添加缓存字典,在其中映射符号,并在必要时添加后缀。你知道吗</p>