简体   繁体   English

PHP:正则表达式匹配完整的匹配括号?

[英]PHP: regex to match complete matching brackets?

In PHP I have the following string: 在PHP中,我有以下字符串:

 $text = "test 1
          {blabla:database{test}}
          {blabla:testing}
          {option:first{A}.Value}{blabla}{option:second{B}.Value}
          {option:third{C}.Value}{option:fourth{D}}
          {option:fifth}
          test 2
         ";

I need to get all { option ...} out of this string (5 in total in this string). 我需要从这个字符串中获取所有{ option ...}(此字符串中共有5个)。 Some have multiple nested brackets in them, and some don't. 有些在它们中有多个嵌套括号,有些则没有。 Some are on the same line, some are not. 有些是在同一条线上,有些则不是。

I already found this regex: 我已经找到了这个正则表达式:

(\{(?>[^{}]+|(?1))*\})

so the following works fine : 以下工作正常:

preg_match_all('/(\{(?>[^{}]+|(?1))*\})/imsx', $text, $matches);

The text that's not inside curly brackets is filtered out, but the matches also include the blabla -items, which I don't need. 过滤掉不在大括号内的文本,但匹配也包括blabla -items,我不需要。

Is there any way this regex can be changed to only include the option -items? 是否有任何方法可以将此正则表达式更改为仅包含option -items?

I modified your initial expression to search for the string '(option:)' appended with non-whitespace characters (\\S*), bounded by curly braces '{}'. 我修改了你的初始表达式,以搜索附加非空白字符(\\ S *)的字符串'(option :)',以花括号'{}'为界。

\{(option:)\S*\}

Given your input text, the following entries are matched in regexpal: 给定输入文本,以下条目在regexpal中匹配:

test 1 测试1

{blabla:database{test}} {布拉布拉:数据库{测试}}

{blabla:testing} {布拉布拉:测试}

{option:first{A}.Value} {option:second{B}.Value} {option:first {A} .Value} {option:second {B} .Value}

{option:third{C}.Value} {选项:第三{C}。价值}

{option:fourth{D}} {选项:第四{d}}

{option:fifth} {选项:第五}

test 2 测试2

Try this regular expression - it was tested using .NET regular expressions, it may work with PHP as well: 试试这个正则表达式 - 它是使用.NET正则表达式测试的,它也可以与PHP一起使用:

\{option:.*?{\w}.*?}

Please note - I'm assuming that you have only 1 pair of brackets inside, and inside that pair you have only 1 alphanumeric character 请注意 - 我假设你里面只有一对支架,在那对里面你只有一个字母数字字符

如果你在同一级别没有多对括号,这应该有效

/(\{option:(([^{]*(\{(?>[^{}]+|(?4))*\})[^}]*)|([^{}]+))\})/imsx

This problem is far better suited to a proper parser, however you can do it with regex if you really want to. 这个问题更适合于正确的解析器,但是如果你真的想要,可以使用正则表达式。

This should work as long as you're not embedding options inside other options. 只要您没有在其他选项中嵌入选项,这应该可以正常工作。

preg_match_all(
    '/{option:((?:(?!{option:).)*)}/',
    $text,
    $matches,
    PREG_SET_ORDER
);

Quick explanation. 快速解释。

{option:               // literal "{option:"
  (                    // begin capturing group
    (?:                // don't capture the next bit
      (?!{option:).    // everything NOT literal "{option:"
    )*                 // zero or more times
  )                    // end capture group
}                      // literal closing brace

var_dump ed output with your sample input looks like: var_dump ed输出与您的示例输入如下:

array(5) {
  [0]=>
  array(2) {
    [0]=>
    string(23) "{option:first{A}.Value}"
    [1]=>
    string(14) "first{A}.Value"
  }
  [1]=>
  array(2) {
    [0]=>
    string(24) "{option:second{B}.Value}"
    [1]=>
    string(15) "second{B}.Value"
  }
  [2]=>
  array(2) {
    [0]=>
    string(23) "{option:third{C}.Value}"
    [1]=>
    string(14) "third{C}.Value"
  }
  [3]=>
  array(2) {
    [0]=>
    string(18) "{option:fourth{D}}"
    [1]=>
    string(9) "fourth{D}"
  }
  [4]=>
  array(2) {
    [0]=>
    string(14) "{option:fifth}"
    [1]=>
    string(5) "fifth"
  }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM