如何匹配'K'、'M'、'G'、'Ki'、'Mi'、'Gi'等而不是单独的'i'词缀
How to match 'K', 'M', 'G', 'Ki', 'Mi', 'Gi' etc. but not solitary 'i' affix
我想要做的是将 shorthand 符号与 ISO 前缀(1k = 1000
、-1ki = -1024
等)相匹配。这个正则表达式很接近:
^([+-]?)(\d+)((?i)[KMGTPEZY]?(?i)i?$)
但它匹配 1i
,所以我试图找到一个正则表达式,如果它前面有字符 class 中的一个字母,它只会匹配 i
。我尝试使用后视:
^([+-]?)(\d+)((?i)[KMGTPEZY]?(?<=(?i)[KMGTPEZY])(?i)i?$)
这不会匹配 1i
,但现在它不会匹配像 1
这样没有前缀的数字,而且似乎...不雅必须重复 [=25] =] 所以我希望有一种更优雅的方式来做到这一点......也适用于 Python :-).
如果它影响答案,完整的问题是我想处理像 1
、2
、3
、[5-10)
、[=30= 这样的事情],1k-2k
,2Mi-3Gi
,10T
...用适当的数字替换前缀 shorthand(1k=1000
、10ki=10240
等)和然后生成实际序列的列表(因此将 [5-10)
扩展为 5,6,7,8,9
,20-25
相当于 [20-25]
或 20,21,22,23,24,25
),但现在,我是在第一步,它只是匹配前缀 shorthand 表示法。
是的,也许可以用奇特的功能来解决这个问题。
但是不,没有必要。
简单的交替就足够了。
^([+-]?\d+)([KMGTPEZY]i|[KMGTPEZY]|)$
也就是说,例如,我们想要匹配 'Ki',或匹配 'K',或匹配...
这其实很简单:
(?i)^([+-])?(\d+)([KMGTPEZY]i?)?$
此处我们指定一个可选组 ([KMGTPEZY]i?)?
,它本身包含可选匹配项 i?
。
请注意,作为全局标志,(?i)
只需指定一次(传统上指定在正则表达式的开头,很容易被发现)。如果你想指定后缀 的可选 i
部分 区分大小写,全局标志对你没有帮助,你必须这样做:
^([+-])?(\d+)([KkMmGgTtPpEeZzYy]i?)?$
示例:
>>> import re
>>> pattern = re.compile('(?i)^([+-])?(\d+)([KMGTPEZY]i?)?$')
>>> pattern.search('12').groups()
(None, '12', None)
>>> pattern.search('-34').groups()
('-', '34', None)
>>> pattern.search('+56m').groups()
('+', '56', 'm')
>>> pattern.search('-78ki').groups()
('-', '78', 'ki')
>>> pattern.search('90i').groups()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'NoneType' object has no attribute 'groups'
我想要做的是将 shorthand 符号与 ISO 前缀(1k = 1000
、-1ki = -1024
等)相匹配。这个正则表达式很接近:
^([+-]?)(\d+)((?i)[KMGTPEZY]?(?i)i?$)
但它匹配 1i
,所以我试图找到一个正则表达式,如果它前面有字符 class 中的一个字母,它只会匹配 i
。我尝试使用后视:
^([+-]?)(\d+)((?i)[KMGTPEZY]?(?<=(?i)[KMGTPEZY])(?i)i?$)
这不会匹配 1i
,但现在它不会匹配像 1
这样没有前缀的数字,而且似乎...不雅必须重复 [=25] =] 所以我希望有一种更优雅的方式来做到这一点......也适用于 Python :-).
如果它影响答案,完整的问题是我想处理像 1
、2
、3
、[5-10)
、[=30= 这样的事情],1k-2k
,2Mi-3Gi
,10T
...用适当的数字替换前缀 shorthand(1k=1000
、10ki=10240
等)和然后生成实际序列的列表(因此将 [5-10)
扩展为 5,6,7,8,9
,20-25
相当于 [20-25]
或 20,21,22,23,24,25
),但现在,我是在第一步,它只是匹配前缀 shorthand 表示法。
是的,也许可以用奇特的功能来解决这个问题。 但是不,没有必要。
简单的交替就足够了。
^([+-]?\d+)([KMGTPEZY]i|[KMGTPEZY]|)$
也就是说,例如,我们想要匹配 'Ki',或匹配 'K',或匹配...
这其实很简单:
(?i)^([+-])?(\d+)([KMGTPEZY]i?)?$
此处我们指定一个可选组 ([KMGTPEZY]i?)?
,它本身包含可选匹配项 i?
。
请注意,作为全局标志,(?i)
只需指定一次(传统上指定在正则表达式的开头,很容易被发现)。如果你想指定后缀 的可选 i
部分 区分大小写,全局标志对你没有帮助,你必须这样做:
^([+-])?(\d+)([KkMmGgTtPpEeZzYy]i?)?$
示例:
>>> import re
>>> pattern = re.compile('(?i)^([+-])?(\d+)([KMGTPEZY]i?)?$')
>>> pattern.search('12').groups()
(None, '12', None)
>>> pattern.search('-34').groups()
('-', '34', None)
>>> pattern.search('+56m').groups()
('+', '56', 'm')
>>> pattern.search('-78ki').groups()
('-', '78', 'ki')
>>> pattern.search('90i').groups()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'NoneType' object has no attribute 'groups'