用于解析重复组的正则表达式

Posted

技术标签:

【中文标题】用于解析重复组的正则表达式【英文标题】:RegEx for parsing repeated groups 【发布时间】:2019-10-18 10:30:57 【问题描述】:

源字符串包含这样的标签:

>>>tagA
contents 1
<<<tagA
...
>>>tagB
contents 2
<<<tagB
...

我需要提取其中的标签名称和内容。这就是我所拥有的,但仍然无法正常工作:

(?<=(>>>(?<tagName>.+)$))(?<contents2>.*?)(?=(<<<.+)$)

results 匹配了两个匹配项,但第二个匹配项中的 tagName 捕获了多行:

tagA 
contents 1 
<<<tagA

我做错了什么?

【问题讨论】:

如果您(似乎)只关心捕获的命名组,为什么还要使用后视/前瞻零长度断言?我是否可能遗漏了您的用例?为什么不“简单地”&gt;&gt;&gt;(?&lt;tagName&gt;[^\n\r]+)[\n\r]+(?&lt;contents&gt;.*?)&lt;&lt;&lt;(需要单行匹配选项);-) 我明白一件事:RegEx 在你完全学会之前真的很痛苦 :) 【参考方案1】:

你可以使用

>>>(?<tagName>.+?)[\r\n]+(?s:(?<contents>.*?))<<<

见regex demo

详情

&gt;&gt;&gt; - &gt;&gt;&gt; 子字符串 (?&lt;tagName&gt;.+?) - 组“tagName”:尽可能少的任何 1+ 个字符 [\r\n]+ - 一个或多个 CR 或 LF 符号 (?s:(?&lt;contents&gt;.*?)) - 组“内容”:匹配任何 0+ 字符的内联修饰符组,但尽可能少 &lt;&lt;&lt; - &lt;&lt;&lt; 子字符串。

在 C# 中:

var matches = Regex.Matches(s, @">>>(?<tagName>.+?)[\r\n]+(?s:(?<contents>.*?))<<<");

见C# demo:

var s = ">>>tagA\ncontents 1\n<<<tagA\n...\n>>>tagB\ncontents 2\n<<<tagB\n...";
var matches = Regex.Matches(s, @">>>(?<tagName>.+?)[\r\n]+(?s:(?<contents>.*?))<<<");
foreach (Match m in matches) 
    Console.WriteLine(m.Groups["tagName"].Value);
    Console.WriteLine(m.Groups["contents"].Value);

输出:

tagA
contents 1

tagB
contents 2

【讨论】:

【参考方案2】:

在这里,我们可能会从一个以&gt;&gt;&gt;&lt;&lt;&lt; 为界的简单表达式开始,可能类似于:

>>>(.+)\s*(.+)\s*<<<.+

我们在这两个捕获组中拥有我们想要的数据:

(.+)

我们将编写剩下的问题。

Demo

测试

using System;
using System.Text.RegularExpressions;

public class Example

    public static void Main()
    
        string pattern = @">>>(.+)\s*(.+)\s*<<<.+";
        string input = @">>>tagA
            contents 1
            <<<tagA

            >>>tagB
            contents 2
            <<<tagB

            >>>tagC

            contents 2

<<<tagC
";
        RegexOptions options = RegexOptions.Multiline;
        
        foreach (Match m in Regex.Matches(input, pattern, options))
        
            Console.WriteLine("'0' found at index 1.", m.Value, m.Index);
        
    

正则表达式电路

jex.im 可视化正则表达式:

【讨论】:

以上是关于用于解析重复组的正则表达式的主要内容,如果未能解决你的问题,请参考以下文章

正则表达式:捕获重复捕获组的所有单个实例 [重复]

用于捕获组的正则表达式无法识别

带有可选匹配组的正则表达式

linux通配符

使用正则表达式从文本文件中解析 [重复]

替代正则表达式以解析链接的 HTML 页面 [重复]