我正在尝试匹配以下文字:
"abc" matches "b" and field[cba] = "cba" or (field[cba] matches "c") and "cc" = "bb"
“匹配”之前和之后的部分到命名组中。
我需要将“abc”与${left}
和“b”匹配为${right}
,然后在第二场比赛中匹配“field [cba]”/“c”。
我需要给${left}
和${right}
提供界限,以便在以下情况下突破:
左:
" and "
," or "
,"("
中的任何一个
右:
" and "
," or "
,")"
我想使用的替换正则表达式模式是:
RegExpMatch(${left}, ${right})
所以要获得以下输出:
RegExpMatch("abc","b") and field[cba] = "cba" or (RegExpMatch(field[cba],"c")) and "cc" = "bb"
我尝试过:
(?<=^|\(| or | and )(?<left>.*?) matches (?<right>.*?)(?=\)|$| and | or )
这有几个问题:
^
作为字符串的开头似乎使得lookbehind贪婪并且它从字符串的开头捕获,即使之前有" or "
或" and "
,这很奇怪因为{{ 1}}似乎工作正常$
," or "
," and "
或"("
仅在不在引号中时(在字面上)匹配你能帮我找出正确的常规模式吗?
答案 0 :(得分:2)
问题是它在您的前瞻中看到and
,然后您使用.*?
(这会吸收所有内容,直到matches
:field[cba] = "cba" or (field[cba]
)。我们需要更严格的左/右定义,它不能只是&#34;任何角色&#34;。
(?<=^|\(| or | and )(?<left>\S+) matches (?<right>\S+?)(?=\)|$| and | or )
我将.*?
更改为\S+
,其匹配任何但空格([^\r\n\t\f ]
)。现在它不会吸收左/右捕获组中的所有不必要的字符。 \S+
可能不是正确的定义,但它应该让您入门。
演示:Regex101
答案 1 :(得分:1)
我不完全确定你的数据是怎样的,但我建议这个正则表达式,它独立于界限:
(?:(?<left>"[^"]*")|\b(?<left>\S*)) matches (?:(?<right>"[^"]*")|(?<right>\S*[^)\s]))
我正在利用C#允许在此处使用相同名称进行捕获的事实。左右两部分几乎相同。
(?: => Non-capture group
(?<left> => Left capture begin
"[^"]*" => Double quotes, non-quote characters then double quotes
) => End left capture
| => OR
\b => Word boundary
(?<left> => Begin other left capture if first failed
\S* => Capture non-space characters (if your parts break on multiple lines, you can use [^"]* instead
) => End left capture
) => End non-capture group
regex101 demo(我更改了命名的捕获,因为PCRE不支持相同的名称捕获组)
如果单词边界导致问题(例如,如果您的某个部分不是以"
或\w
字符开头,则可以使用以下正则表达式:
(?:(?<left>"[^"]*")|\s\(?(?<left>\S*)) matches (?:(?<right>"[^"]*")|(?<right>\S*[^)\s]))
使用\s\(?
代替\b
如果你想坚持你提到的界限,你将不得不知道零件中究竟可以是什么,或者什么不可以。例如,如果
field["abc"] in field matches field["cba"] in field
有效且部分分别为field["abc"] in field
和field["cba"] in field
,那么它是另一个complication.