我在python中遇到一个问题,创建一个正则表达式来获取与正则表达式匹配的每个出现。 我有这个代码,我需要帮助。
strToSearch= "1A851B 1C331 1A3X1 1N111 1A3 and a whole lot of random other words."
print(re.findall('\d{1}[A-Z]{1}\d{3}', strToSearch.upper())) #1C331, 1N111
print(re.findall('\d{1}[A-Z]{1}\d{1}[X]\d{1}', strToSearch.upper())) #1A3X1
print(re.findall('\d{1}[A-Z]{1}\d{3}[A-Z]{1}', strToSearch.upper())) #1A851B
print(re.findall('\d{1}[A-Z]{1}\d{1}', strToSearch.upper())) #1A3
>['1A851', '1C331', '1N111']
>['1A3X1']
>['1A851B']
>['1A8', '1C3', '1A3', '1N1', '1A3']
正如你所看到的,它在第一个中返回“1A851”,我不希望它。如何防止它出现在第一个正则表达式?有些事情你可以知道它可能出现在字符串中,如“单词1A851B?”所以我需要保持标点不被抓住。
另外,我如何将这些组合成一个正则表达式。基本上我的最终目标是在python中运行if语句,类似于下面的伪代码。
lstResults = []
strToSearch= " Alot of 1N1X1 people like to eat 3C191 cheese and I'm a 1A831B aka 1A8."
lstResults = re.findall('<REGEX HERE>', strToSearch)
for r in lstResults:
print(r)
所需的输出将是
1N1X1
3C191
1A831B
1A8
答案 0 :(得分:0)
Yo可能会使用单词边界:
\b\d{1}[A-Z]{1}\d{3}\b
请参阅demo
对于组合,根据您考虑单词“随机单词”的标准尚不清楚,但您可以使用以下内容:
[A-Z\d]*\d[A-Z\d]*[A-Z][A-Z\d]*
这是一个包含至少一个数字和至少一个非数字字符的单词。请参阅demo。
或许你可以使用:
\b\d[A-Z\d]*[A-Z][A-Z\d]*
dor一个以数字开头且至少包含非数字字符的单词。请参阅demo。
或者,如果您想要正确组合这些正则表达式,请使用。
\b\d[A-Z]\d(X\d|\d{2}[A-Z]?)?\b
查看最终demo。
答案 1 :(得分:0)
使用单个正则表达式模式:
strToSearch= " Alot of 1N1X1 people like to eat 3C191 cheese and I'm a 1A831B aka 1A8."
lstResults = [i[0] for i in re.findall(r'(\d[A-Z]\d{1,3}(X\d|[A-Z])?)', strToSearch)]
print(lstResults)
输出:
['1N1X1', '3C191', '1A831B', '1A8']
答案 2 :(得分:0)
如果你想找到混合了数字和字母的“单词”,最简单的方法是使用单词边界算子\b
;但请注意,您需要使用r''
字符串/转义代码中的\
(在将来的Python版本中,无论如何都需要为\d
执行此操作)。要匹配由单词边界分隔的任何字母数字字符序列,您可以使用
r'\b[0-9A-Z]+\b'
但是,这还不能保证至少有一个号码和至少一个字母。为此,我们将使用正零宽度前瞻断言(?= )
,这意味着只有当包含的模式在该点匹配时,整个正则表达式才匹配。我们需要其中两个:一个确保至少有一个数字,一个至少有一个字母:
>>> p = r'\b(?=[0-9A-Z]*[0-9])(?=[0-9A-Z]*[A-Z])[0-9A-Z]+\b'
>>> re.findall(p, '1A A1 32 AA 1A123B')
['1A', 'A1', '1A123B']
只要至少有一位数字和一个字母,现在就会匹配包括33333A
或AAAAAAAAAA3A
在内的所有内容。但是,如果模式始终以数字开头并且始终包含字母,则会变得稍微容易一些,例如:
>>> p = r'\b\d+[A-Z][0-9A-Z]*\b'
>>> re.findall(p, '1A A1 32 AA 1A123B')
['1A', '1A123B']
即。 A1不匹配,因为它不是以数字开头。