用于仅匹配粘在一起的大写单词的正则表达式(即不被空格分隔)
Regex for matching only capitalized words stuck together (i.e. not separated by whitespace)
我有一长串字符串,都是随机的单词,全部大写,比如'Pomegranate'
和'Yellow Banana'
。但是,其中一些粘在一起,例如:'AppleOrange'
。没有特殊字符或数字。
我需要的是 Python 上的正则表达式,分别匹配 'Apple'
和 'Orange'
,但不匹配 'Pomegranate'
或 'Yellow'
.
不出所料,我对此很陌生,我只写了 r"(?<!\s)([A-Z][a-z]*)"
... 但它仍然匹配 'Yellow'
和 'Pomegranate'
。我该怎么做?
如果它们都以大写字符和可选的小写字符开头,您可以使用环视和交替来匹配这两种变体
(?<=[a-z])[A-Z][a-z]*|[A-Z][a-z]*(?=[A-Z])
模式匹配:
(?<=[a-z])
向左断言 a-z
[A-Z][a-z]*
匹配 A-Z 和可选字符 a-z
|
或
[A-Z][a-z]*
匹配 A-Z 和可选字符 a-z
(?=[A-Z])
向右断言 A-Z
例子
import re
pattern = r"(?<=[a-z])[A-Z][a-z]*|[A-Z][a-z]*(?=[A-Z])"
s = ("AppleOrange\nPomegranate Yellow Banana")
print(re.findall(pattern, s))
输出
['Apple', 'Orange']
另一种选择可能是通过匹配来避开您不想要的内容,并使用捕获组来保存您想要保留的内容并从结果中删除空条目:
(?<!\S)[A-Z][a-z]*(?!\S)|([A-Z][a-z]*)
import re
pattern = r"(?<!\S)[A-Z][a-z]*(?!\S)|([A-Z][a-z]*)"
s = ("AppleOrange\nPomegranate Yellow Banana")
print([x for x in re.findall(pattern, s) if x])
这项工作:
import re
from collections import deque
pattern = r'([A-Z]{2,}(?=[A-Z]|$)|[A-Z](?=[a-z]|$))'
chunks = deque(re.split(pattern, 'AppleOrange'))
result = []
while len(chunks):
buf = chunks.popleft()
if len(buf) == 0:
continue
if re.match(r'^[A-Z]$', buf) and len(chunks):
buf += chunks.popleft()
result.append(buf)
print(result)
输出:
['Apple', 'Orange']
检查 OP here
我有一长串字符串,都是随机的单词,全部大写,比如'Pomegranate'
和'Yellow Banana'
。但是,其中一些粘在一起,例如:'AppleOrange'
。没有特殊字符或数字。
我需要的是 Python 上的正则表达式,分别匹配 'Apple'
和 'Orange'
,但不匹配 'Pomegranate'
或 'Yellow'
.
不出所料,我对此很陌生,我只写了 r"(?<!\s)([A-Z][a-z]*)"
... 但它仍然匹配 'Yellow'
和 'Pomegranate'
。我该怎么做?
如果它们都以大写字符和可选的小写字符开头,您可以使用环视和交替来匹配这两种变体
(?<=[a-z])[A-Z][a-z]*|[A-Z][a-z]*(?=[A-Z])
模式匹配:
(?<=[a-z])
向左断言 a-z[A-Z][a-z]*
匹配 A-Z 和可选字符 a-z|
或[A-Z][a-z]*
匹配 A-Z 和可选字符 a-z(?=[A-Z])
向右断言 A-Z
例子
import re
pattern = r"(?<=[a-z])[A-Z][a-z]*|[A-Z][a-z]*(?=[A-Z])"
s = ("AppleOrange\nPomegranate Yellow Banana")
print(re.findall(pattern, s))
输出
['Apple', 'Orange']
另一种选择可能是通过匹配来避开您不想要的内容,并使用捕获组来保存您想要保留的内容并从结果中删除空条目:
(?<!\S)[A-Z][a-z]*(?!\S)|([A-Z][a-z]*)
import re
pattern = r"(?<!\S)[A-Z][a-z]*(?!\S)|([A-Z][a-z]*)"
s = ("AppleOrange\nPomegranate Yellow Banana")
print([x for x in re.findall(pattern, s) if x])
这项工作:
import re
from collections import deque
pattern = r'([A-Z]{2,}(?=[A-Z]|$)|[A-Z](?=[a-z]|$))'
chunks = deque(re.split(pattern, 'AppleOrange'))
result = []
while len(chunks):
buf = chunks.popleft()
if len(buf) == 0:
continue
if re.match(r'^[A-Z]$', buf) and len(chunks):
buf += chunks.popleft()
result.append(buf)
print(result)
输出:
['Apple', 'Orange']
检查 OP here