Python正则表达式:如果括号和引号存在,如何提取它们之间的字符串

2024-09-29 23:31:12 发布

您现在位置:Python中文网/ 问答频道 /正文

我试图提取Jenkinsfiles中每个触发器的值/参数,如果存在的话,它们位于括号和引号之间。你知道吗

例如,给定以下条件:

upstream(upstreamProjects: 'upstreamJob', threshold: hudson.model.Result.SUCCESS)  # just parentheses
pollSCM('H * * * *')     # single quotes and parentheses

期望结果分别为:

upstreamProjects: 'upstreamJob', threshold: hudson.model.Result.SUCCESS
H * * * *

我当前的结果:

upstreamProjects: 'upstreamJob', threshold: hudson.model.Result.SUCCESS
H * * * *'        # Notice the trailing single quote

到目前为止,我已经成功地使用了第一个触发器(上游触发器),但是没有成功地使用第二个触发器(pollSCM),因为后面还有一个单引号。你知道吗

在组(.+)之后,它不捕获带有\'*的尾随单引号,而是捕获带有\)的右括号。我可以简单地使用.replace()或.strip()来删除它,但是我的正则表达式模式有什么问题吗?我怎样才能改进它?这是我的密码:

pattern = r"[A-Za-z]*\(\'*\"*(.+)\'*\"*\)"
text1 = r"upstream(upstreamProjects: 'upstreamJob', threshold: hudson.model.Result.SUCCESS)"
text2 = r"pollSCM('H * * * *')"
trigger_value1 = re.search(pattern, text1).group(1)
trigger_value2 = re.search(pattern, text2).group(1)

Tags: thresholdmodelresult括号successpattern触发器upstream
3条回答
import re
s = """upstream(upstreamProjects: 'upstreamJob', threshold: hudson.model.Result.SUCCESS)  # just parentheses
pollSCM('H * * * *')"""
print(re.findall("\((.*?)\)", s))

输出:

["upstreamProjects: 'upstreamJob', threshold: hudson.model.Result.SUCCESS", "'H * * * *'"]

例如,您的数据可以使'成为可选的'?,并在一个组中捕获您的值,然后在捕获的组中循环。你知道吗

^{}

test_str = ("upstream(upstreamProjects: 'upstreamJob', threshold: hudson.model.Result.SUCCESS)  # just parentheses\n"
    "pollSCM('H * * * *')     # single quotes and parentheses")

matches = re.finditer(regex, test_str, re.MULTILINE)

for matchNum, match in enumerate(matches):    
    for groupNum in range(0, len(match.groups())):
        groupNum = groupNum + 1  
        print (match.group(groupNum))

Demo Python

这会给你:

upstreamProjects: 'upstreamJob', threshold: hudson.model.Result.SUCCESS
H * * * *

要获得更严格的匹配,您可以使用交替来匹配()(''),但不能使用像('H * * * *)这样的单个',然后遍历捕获的组。因为您现在捕获了2个组,其中1个组是空的,所以您可以检查是否只检索非空组。你知道吗

^{}

Demo Python

你的\'*部分意味着0 or more matches代表你的单勾,所以.+会抓住最后一个',因为它是贪婪的。您需要将?添加到(.+),这样它才不会贪婪。基本上,它意味着抓住一切,直到它遇到'。你知道吗

此模式适用于您: [A-Za-z]*\(\'*\"*(.+?)\'*\"*\)

[更新]

为了回答你下面的问题,我在这里加上它。你知道吗

So the ? will make it not greedy up until the next character indicated in the pattern?

是的,它基本上将重复操作符更改为不贪婪(懒惰量词),因为默认情况下它们是贪婪的。因此.*?a将匹配所有内容直到第一个a,而.*a将匹配所有内容,包括在字符串中找到的任何a,直到它无法再与字符串匹配为止。因此,如果字符串是aaaaaaaa,正则表达式是.*?a,那么它实际上会匹配每个a。例如,如果对字符串aaaaaaaa上的每个匹配使用.*?ab替换,您将得到字符串bbbbbbbb.*a但是在具有相同替换的字符串aaaaaaaa上,将返回单个b。你知道吗

下面的链接解释了不同的量词类型(贪婪、懒惰、所有格):http://www.rexegg.com/regex-quantifiers.html

相关问题 更多 >

    热门问题