给定一个带有数字的字符串:
I counted, ' 1 2 3 4 5 5 5 8 9 10 '
目标是将数字转换为 _NUM-*_
符号,其中 *
表示数字出现的顺序。例如。给定上述 intpu 所需的输出是:
"I counted, ' _NUM-1_ _NUM-2_ _NUM-3_ _NUM-4_ _NUM-5_ _NUM-6_ _NUM-7_ _NUM-8_ _NUM-9_ _NUM-10_'"
即使是重复的数字,例如给定输入
I said, ' 1 2 3 4 5 5 5 8 9 10 '
所需的输出保持数字的顺序,忽略数字本身的值,例如:
"I said, ' _NUM-1_ _NUM-2_ _NUM-3_ _NUM-4_ _NUM-5_ _NUM-6_ _NUM-7_ _NUM-8_ _NUM-9_ _NUM-10_'"
我已经尝试过:
import re
s = "I counted, ' 1 2 3 4 5 6 7 8 9 10 '"
num_regexp = '(?<!\S)(?=.)(0|([1-9](\d*|\d{0,2}(,\d{3})*)))?(\.\d*[1-9])?(?!\S)'
re.sub(num_regexp, '_NUM_', s)
但它只是用相同的 _NUM_
符号替换输出,而不保持顺序,即
[输出]:
"I counted, ' _NUM_ _NUM_ _NUM_ _NUM_ _NUM_ _NUM_ _NUM_ _NUM_ _NUM_ _NUM_ _NUM_ '"
我可以执行 post re.sub
操作并替换每个 _NUM_
,即
import re
s = "I counted, ' 1 2 3 4 5 6 7 8 9 10 '"
num_regexp = '(?<!\S)(?=.)(0|([1-9](\d*|\d{0,2}(,\d{3})*)))?(\.\d*[1-9])?(?!\S)'
num_counter = 1
tokens = []
for token in re.sub(num_regexp, '_NUM_', s).split():
if token == '_NUM_':
token = '_NUM-{}_'.format(num_counter)
num_counter += 1
tokens.append(token)
result = ' '.join(tokens)
[输出]:
"I counted, ' _NUM-1_ _NUM-2_ _NUM-3_ _NUM-4_ _NUM-5_ _NUM-6_ _NUM-7_ _NUM-8_ _NUM-9_ _NUM-10_ '"
是否有更好的方法来实现所需的输出,而无需先进行通用 re.sub
然后进行事后字符串编辑?
最佳答案
使用itertools.count
作为传递给 re.sub
的函数的默认参数。
>>> from itertools import count
>>> re.sub('(\d+)', lambda m, c=count(1): '_NUM_-{}'.format(next(c)), s)
' _NUM_-1 _NUM_-2 _NUM_-3 _NUM_-4 _NUM_-5 _NUM_-6 _NUM_-7 _NUM_-8 _NUM_-9 _NUM_-10 '
请注意,我使用简化的正则表达式来匹配数字只是为了演示如何获取计数,您可以将其替换为也匹配 float 的正则表达式。
关于python - 将字符串中的数字转换为 `_NUM-*_` 符号,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45626038/