首页 > 解决方案 > 正则表达式捕获组

问题描述

假设我有这个虚拟 URL,我需要将植物及其颜色提取为capture groups

https://flowers.com/compare._plant1.green.402992_plant2.yellow.402228_plant3.red.403010_plant4.orange.399987.html

我所拥有的以下内容regex是按预期捕获我需要的元素,但是当我在 URL 中的植物少于 4 个时无法捕获任何内容。底部有一个正则表达式测试器的链接,其中包含您可以使用的示例代码和 URL。

如何修改此正则表达式以动态工作,以便在不需要静态 URL 结构的情况下捕获可用内容。现在,假设我最多只捕获 4 株植物(8 组)

(flowers\.com)\/compare\._(?:([^.]+)\.([^.]+)).*_(?:([^.]+)\.([^.]+)).*_(?:([^.]+)\.([^.]+)).*_(?:([^.]+)\.([^.]+))

在此处输入图像描述

https://regex101.com/r/prjAO7/2

标签: pythonregexregex-group

解决方案


您可以匹配第一个植物,并使用问号非捕获组使第二个、第三个和第四个可选(?:..)?

除了使用.*你还可以匹配一个点和 1+ 个数字,而不是使用\.\d+来防止不必要的回溯。

(flowers\.com)\/compare\._([^.]+)\.([^.]+)\.\d+(?:_([^.]+)\.([^.]+)\.\d+)?(?:_([^.]+)\.([^.]+)\.\d+)?(?:_([^.]+)\.([^.]+)\.\d+)?

正则表达式演示


如果您已经知道它是flowers.comurl 并获取路径,另一种选择是解析 url 。如果花朵的部分以相同的方式构造,您也可以使用图案的单个部分_([^.]+)\.([^.]+)\.\d+

Python 演示

例如

from urllib.parse import urlparse
import re

pattern = r"_([^.]+)\.([^.]+)\.\d+"

o = urlparse('https://flowers.com/compare._plant1.green.402992_plant2.yellow.402228_plant3.red.403010_plant4.orange.399987.html')
print(re.findall(pattern, o.path))

输出

[('plant1', 'green'), ('plant2', 'yellow'), ('plant3', 'red'), ('plant4', 'orange')]

推荐阅读