编写表达式以递归地提取括号之间的数据

Writing an expression to recursively extract data between parenthesis

我正在尝试编写一个正则表达式来将字符串拆分为匹配花括号内的单独元素。首先,它需要递归,其次,它必须 return 偏移量(就像 PREG_OFFSET_CAPTURE)。

我实际上认为这可能是处理这些数据的一种效率较低的方法,但我不确定是否有一种更简单、更受性能驱动的技术。 (如果你有,我很想听听!)

因此,输入可以采用以下格式:

Hello {#name}! I'm a {%string|sentence|bit of {#random} text}

如果数据采用这种格式,处理数据就足够简单了:

Hello {#name}! I'm a {%string|sentence|bit of random text}

但处理时的问题是另一组花括号中的递归花括号。 我正在使用以下代码拆分字符串:

preg_match_all("/(?<={)[^}]*(?=})/m", $string, $braces, PREG_OFFSET_CAPTURE);

如前所述,简单的形式非常好。对于更复杂的形式,情况就更少了。这样做的目的(我让它以非递归形式运行)是用函数处理的内容替换每个括号内的区域,向上工作。

理想情况下,我希望能够编写 Hello {#name}! I'm a {%string|sentence|bit of {?(random == "strange") ? {#random} : "strange"}} text} 并且易于管理。

非常感谢任何帮助。

您可以利用 PCRE 正则表达式在前瞻和子例程中捕获组的能力来获取嵌套的 {...} 子字符串。

一个regex demo is available here.

$re = "#(?=(\{(?>[^{}]|(?1))*+\}))#"; 
$str = "Hello {#name}! I'm a {%string|sentence|bit of {#random} text}"; 
preg_match_all($re, $str, $matches, PREG_OFFSET_CAPTURE);
print_r($matches[1]);

IDEONE demo

它将 return 一个数组,其中包含捕获的类似 {...} 的字符串及其位置:

Array
(
    [0] => Array
        (
            [0] => {#name}
            [1] => 6
        )

    [1] => Array
        (
            [0] => {%string|sentence|bit of {#random} text}
            [1] => 21
        )

    [2] => Array
        (
            [0] => {#random}
            [1] => 46
        )

)