1

我正在尝试在字符串上使用更复杂的正则表达式和 preg_split 来获取所有匹配项的数组并保留分隔符。通常这很简单,但尝试使用 PREG_SPLIT_DELIM_CAPTURE 并在我的正则表达式中使用多组括号被证明是困难的。我会详细说明:

我想在一行中解析一个 IP 地址并将整行分成一个数组,这样我就可以只使用 IP 做一些事情,但我想最终显示整行(我正在对 IP 应用格式,然后重新-组装和显示字符串)。我的正则表达式是这样的(它检查看起来像 IP 的东西,但它不检查有效性,我现在不在乎):

(((\d{1,3})\.){3}(\d{1,3}))

现在,我的代码暂时是这样的: $ipv4regex = "/(((\d{1,3}).){3}(\d{1,3}))/";

if (contains_ipv4($line)){
    $pieces = preg_split($ipv4regex, $line, 0, PREG_SPLIT_DELIM_CAPTURE);
    print "<pre>";
    print_r($pieces);
    print "</pre>";
}

function contains_ipv4($val){
    return (preg_match($ipv4regex, $val));
}

这是我的输出示例(IP 地址已更改,但仍然相关):

Array
(
    [0] => show arp results from 
    [1] => 10.10.15.120
    [2] => 15.
    [3] => 15
    [4] => 120
    [5] => 
)

我怎样才能改变它,使输出如下:

(
    [0] => show arp results from 
    [1] => 10.10.15.120
    [2] => 
)

本质上,我只想捕获 PREG_SPLIT_DELIM_CAPTURE 正则表达式中最外层的括号,而不是内部的括号。我知道我可以针对这种特殊情况更改我的正则表达式,但是我有一个带有很多括号的“正确”IPv6 正则表达式,我担心只用一组括号重写几乎是不可能的外部。谁能帮帮我?我将不胜感激。或者,如果我错过了一种完全不同的方式来达到我的目的,请随时指出我的方向。

4

2 回答 2

0

您可以通过在开括号后添加来停用括号捕获?:,例如:

((?:(?:\d{1,3})\.){3}(?:\d{1,3}))
于 2012-08-29T15:18:16.077 回答
0

我设法减少了该方法的整体混乱并对其进行了改进以仅使用几行代码:

if (preg_match($ipv4regex, $line)){
    $line = preg_replace_callback($ipv4regex, 'add_ipv4_p', $line);
}

然后我稍后打印该行,但是这个简单的位就是我所需要的正则表达式检查方法 add_ipv4_p 是我用来将格式应用于传递给它的数组的第一个元素的方法。简单的。通过重新使用此代码段并更改正则表达式和格式化方法,我能够为代码添加更多格式化选项。

于 2012-08-30T14:05:21.217 回答