替换正则表达式循环中的组
replace groups in regex loop
我有这两行:
What is P(output1|cause1=2, cause2=2)
What is P(output2|cause3=2)
我想改成:
method_to_use(model, {"cause1": 2, "cause2": 2}, "output1")
method_to_use(model, {"cause3": 2}, "output2")
这是我的正则表达式:
.*P[(]([a-z1-9]+)[|](([a-z1-9]+)=([1-9]),?)+[)]
我尝试这样替换它:
method_to_use(model, {"": }, "")
但我只得到最后一组:
method_to_use(model, {"cause2": 2}, "output1")
是否可以做某种 "loop" 并在途中改变所有适合度?
有一件事是肯定的:你不能用一个正则表达式来做到这一点。
您可以使用三步法:
- 将
.*P\(
替换为method_to_use(
- 将
\(\K(\w+)\|([^()]+)
替换为model, {}, ""
- 将
(\w+)=(\w+)
替换为"":
请注意
.*P\(
尽可能多地匹配换行字符以外的任何 0 个或多个字符,并且 P(
\(\K(\w+)\|([^()]+)
匹配(
,然后从\K
的匹配值中丢弃,然后将1+字的字符抓取到Group 1中(</code>中的替换模式),<code>|
被匹配,然后 )
和 (
以外的 1+ 个字符被捕获到第 2 组(</code>)</li>
<li><code>(\w+)=(\w+)
- 1+ 个单词字符被捕获到第 1 组(替换模式中的 </code>),<code>=
被匹配,然后 1+ 个单词字符被捕获到第 2 组(
).
您可以使用以下正则表达式匹配字符串。
^.*P\(([^|]+)\|([^=]+)=(\d+)(?:, +([^=]+)=(\d+))?\)$
如果捕获组 4 非空,则将(整个字符串)匹配替换为
method_to_use(model, {"": , "": }, "")
这会导致字符串
What is P(output1|cause1=2, cause2=2)
将替换为
method_to_use(model, {"cause1": 2, "cause2": 2}, "output1")
如果捕获组 4 为空,则将匹配项替换为
method_to_use(model, {"": }, "")
这会导致字符串
What is P(output2|cause3=2)
将替换为
method_to_use(model, {"cause3": 2}, "output2")
请注意,两个链接的正则表达式是等价的,唯一的区别是在 Demo 1 中,我用 free-spacing mode 表达正则表达式,这允许它是自我记录。
当然可以简单地从捕获组的值中形成新的字符串,而不是替换整个字符串。如果这样做,正则表达式开头的 ^.*P
可以简单地更改为 P
.
正则表达式引擎执行以下操作。
^ # match beginning of line
.*P\( # match 0+ chars then '|('
([^|]+) # save 1+ chars except '|' in cap grp 1 (output)
\| # match ':'
([^=]+) # save 1+ chars except '=' in cap grp 2 (causeA)
= # match '='
(\d+) # save 1+ digits in cap grp 3 (causeAval)
(?: # begin non-cap grp
,\ + # match ',' then 1+ spaces
([^=]+) # match 1+ chars except '=' in cap grp 4 (causeB)
= # match '='
(\d+) # match 1+ digits in cap grp 5 (causeBval)
)? # end non-cap grp and make it optional
\) # match ')'
$ # match end of line
我有这两行:
What is P(output1|cause1=2, cause2=2)
What is P(output2|cause3=2)
我想改成:
method_to_use(model, {"cause1": 2, "cause2": 2}, "output1")
method_to_use(model, {"cause3": 2}, "output2")
这是我的正则表达式:
.*P[(]([a-z1-9]+)[|](([a-z1-9]+)=([1-9]),?)+[)]
我尝试这样替换它:
method_to_use(model, {"": }, "")
但我只得到最后一组:
method_to_use(model, {"cause2": 2}, "output1")
是否可以做某种 "loop" 并在途中改变所有适合度?
有一件事是肯定的:你不能用一个正则表达式来做到这一点。
您可以使用三步法:
- 将
.*P\(
替换为method_to_use(
- 将
\(\K(\w+)\|([^()]+)
替换为model, {}, ""
- 将
(\w+)=(\w+)
替换为"":
请注意
.*P\(
尽可能多地匹配换行字符以外的任何 0 个或多个字符,并且P(
\(\K(\w+)\|([^()]+)
匹配(
,然后从\K
的匹配值中丢弃,然后将1+字的字符抓取到Group 1中(</code>中的替换模式),<code>|
被匹配,然后)
和(
以外的 1+ 个字符被捕获到第 2 组(</code>)</li> <li><code>(\w+)=(\w+)
- 1+ 个单词字符被捕获到第 1 组(替换模式中的</code>),<code>=
被匹配,然后 1+ 个单词字符被捕获到第 2 组().
您可以使用以下正则表达式匹配字符串。
^.*P\(([^|]+)\|([^=]+)=(\d+)(?:, +([^=]+)=(\d+))?\)$
如果捕获组 4 非空,则将(整个字符串)匹配替换为
method_to_use(model, {"": , "": }, "")
这会导致字符串
What is P(output1|cause1=2, cause2=2)
将替换为
method_to_use(model, {"cause1": 2, "cause2": 2}, "output1")
如果捕获组 4 为空,则将匹配项替换为
method_to_use(model, {"": }, "")
这会导致字符串
What is P(output2|cause3=2)
将替换为
method_to_use(model, {"cause3": 2}, "output2")
请注意,两个链接的正则表达式是等价的,唯一的区别是在 Demo 1 中,我用 free-spacing mode 表达正则表达式,这允许它是自我记录。
当然可以简单地从捕获组的值中形成新的字符串,而不是替换整个字符串。如果这样做,正则表达式开头的 ^.*P
可以简单地更改为 P
.
正则表达式引擎执行以下操作。
^ # match beginning of line
.*P\( # match 0+ chars then '|('
([^|]+) # save 1+ chars except '|' in cap grp 1 (output)
\| # match ':'
([^=]+) # save 1+ chars except '=' in cap grp 2 (causeA)
= # match '='
(\d+) # save 1+ digits in cap grp 3 (causeAval)
(?: # begin non-cap grp
,\ + # match ',' then 1+ spaces
([^=]+) # match 1+ chars except '=' in cap grp 4 (causeB)
= # match '='
(\d+) # match 1+ digits in cap grp 5 (causeBval)
)? # end non-cap grp and make it optional
\) # match ')'
$ # match end of line