提取由 space 分隔的组

Extract groups separated by space

我有以下字符串(示例):

Loader[data-prop data-attr="value"]

可以有 1 - n 个属性。我想提取每个属性。 (数据属性,数据属性="value")。我尝试了很多不同的方式,例如 \[(?:(\S+)\s)*\] 但我没有做对。表达式应该写成PREG风格..

怎么样 [\s\[]([^\s\]]+(="[^"]+)*)+

给予

第 1 场比赛:data-prop

第 2 场比赛:data-attr="value"

我建议使用正则表达式获取所有键值对:

'~(?:([^][]*)\b\[|(?!^)\G)\s*(\w+(?:-\w+)*(?:=(["\'])?[^\]]*?)?)~'

(参见 regex demo)然后

IDEONE demo

$re = '~(?:([^][]*)\b\[|(?!^)\G)\s*(\w+(?:-\w+)*(?:=(["\'])?[^\]]*?)?)~'; 
$str = "Loader[data-prop data-attr=\"value\" more-here='data' and-one-more=\"\"]"; 
preg_match_all($re, $str, $matches);
$arr = array();
for ($i = 0; $i < count($matches); $i++) {
    if ($i != 0) {
        $arr = array_merge(array_filter($matches[$i]),$arr);
    }
}
print_r(preg_grep('~\A(?![\'"]\z)~', $arr));

输出:

Array
(
    [3] => data-prop
    [4] => data-attr="value"
    [5] => more-here='data'
    [6] => and-one-more=""
    [7] => Loader
)

关于正则表达式的注释(它看起来太复杂了):

  • (?:([^][]*)\b\[|(?!^)\G) - 一个边界:我们只从 [ 开始匹配,这个 [ 前面有一个单词 (a-zA-Z0-9_) 字符(有 \b\[),或者右边成功匹配后((?!^)\G)。 此外,([^][]*) 会将 [ 之前的部分捕获到组 1 中。
  • \s* - 匹配零个或多个空白符号
  • (\w+(?:-\w+)*) - 捕获到第 2 组 "words",如 "word1" 或 "word1-word2"..."word1-wordn"
  • (?:=(["\'])?[^\]]*?)? - 可选组(由于 (?:...)?)匹配
    • = - 等号
    • (["\'])? - 第 3 组(检查值定界符的辅助组)捕获 "' 或什么都不捕获
    • [^\]]*? - (值)零个或多个 ] 以外的字符尽可能少
    • </code> - 结束 <code>'"(在第 3 组中捕获的相同值)。

由于我们无法摆脱捕获 '",我们可以 preg_grep 我们不感兴趣的所有元素 preg_grep('~\A(?![\'"]\z)~', $arr) where \A(?![\'"]\z) 匹配任何不等于 '".

的字符串