代码之家  ›  专栏  ›  技术社区  ›  PNS

Regex对多行字符串进行分区

  •  0
  • PNS  · 技术社区  · 9 年前

    考虑一个由以下内容组成的多行字符串 N lines ,如下所示:

    Line 1 text
    Line 2 text
    Line 3 text
    ...
    Line n-1 text
    Line n text
    anchor=value
    Line n+2 text
    Line n+3 text
    Line n+4 text
    ...
    Line N text
    

    这个 anchor 键不会出现在任何行内,在锚之前以及锚周围可能有空格 = 后面的符号。

    我需要一个正则表达式,将上述字符串分成3组:

    1. 第1行至第n行(含)
    2. 锚定线(分隔点)
    3. 第n+2行至第n行(含)

    我最接近的解决方案是

    (?s)^(?:(?!anchor\s*=\s*).)+?\r|\nanchor\s*=\s*([^\r\n]+)(?:\r|\n)(.*)
    

    但是上面的正则表达式包括第一个匹配组中的整个文本,并按预期填充剩余的2个组。

    另外一个要求是正则表达式必须尽可能快,因为它将应用于大量数据。还要注意,在此用例中,通过单个正则表达式进行处理是唯一的选项。

    有什么想法吗?

    3 回复  |  直到 9 年前
        1
  •  2
  •   Wiktor Stribiżew    9 年前

    这个正则表达式呢?

    (?s)^(.*?)(anchor\s*\=\s*[^\r\n]+)(.*?)

    或者,为了匹配字符串的结尾,

    (?s)^(.*?)(anchor\s*\=\s*[^\r\n]+)(.*?)$ ?

        2
  •  1
  •   RudolphEst    9 年前

    如果您需要速度庞大的字符串,正则表达式是不可取的。您必须将整个字符串存储在内存中,才能使用正则表达式对其进行标记。我建议改用Reader/InputStreams。

        3
  •  1
  •   Bohemian    9 年前

    好吧,你可以先找到锚,然后在上面拆分:

    String anchor = str.replaceAll("(?ms).*?(anchor\\s*=.*?)$.*", "$1");
    String lineParts = str.split("\\Q" + anchor + "\\E");
    

    “m”标志使^和$匹配行的开始/结束。