php preg_match_all 需要多个结果
php preg_match_all need multiple results
我想要 preg_match_all
到 return 它找到的所有模式,即使结果已经被使用。下面的示例隔离了问题。
$str = "whatever aaa 34567 aaa 56789 ll";
$pattern = '/.{0,100}\D[aaa]{3}\D{1}[0-9]{5}\D{1}/';
preg_match_all($pattern, $str, $amatches);
var_dump($amatches);
以上return个数组元素的结果。
0=> `whatever aaa 34567 aaa 56789 `
我要的是2个数组元素。
0=> `whatever aaa 34567`
1=> `whatever aaa 34567 aaa 56789`
这个更近一点:
$str = "whatever aaa 34567 aaa 56789 ll";
$pattern = '/^((.*)\D[aaa]{3}\D{1}[0-9]{5}\D{1})?/';
preg_match($pattern, $str, $amatches);
var_dump($amatches);
returns
array(3) {
[0] => string(29) "whatever aaa 34567 aaa 56789 "
[1] => string(29) "whatever aaa 34567 aaa 56789 "
[2] => string(18) "whatever aaa 34567"
}
或者这仍然使用 preg_match_all:
$str = "whatever aaa 34567 aaa 56789 ll";
$pattern = '/^((.*)\D[aaa]{3}\D{1}[0-9]{5}\D{1})?/';
preg_match_all($pattern, $str, $amatches);
var_dump($amatches);
我认为正在发生的事情是您的 .{0,100} 正在被通读整个内容,而根本不允许正则表达式在最后启动。这 ?确保它以您的模式结尾。
这是使用 preg_replace_callback 完成这项工作的替代解决方案。
- 查找匹配 "any characters followed by (and including) three 'a' characters, some space and five digits" 的字符串。可能有尾随空格。
\b
表示单词边界,防止匹配 "xaaa 12345"、"aaa 123456" 或 "aaa 12345xyz"
- 将匹配字符串连接到
$soFar
,其中包含任何先前匹配的字符串
- 将该字符串附加到
$result
数组
我不太确定你是否希望 "foo"s 和 "bar"s 保留在字符串中,所以我把它们留在了。
$str = "whatever foo aaa 12345 bar aaa 34567 aaa 56789 baz fez";
preg_replace_callback(
'/.*?\baaa +\d{5}\b\s*/',
function ($matches) use (&$result, &$soFar) {
$soFar .= $matches[0];
$result[] = trim($soFar);
}, $str
);
print_r($result);
输出:
Array
(
[0] => whatever foo aaa 12345
[1] => whatever foo aaa 12345 bar aaa 34567
[2] => whatever foo aaa 12345 bar aaa 34567 aaa 56789
)
使用 preg_match_all and array_map 的两步版本:
preg_match_all('/.*?\baaa +\d{5}\b\s*/', $str, $matches);
$matches = array_map(
function ($match) use (&$soFar) {
$soFar .= $match;
return trim($soFar);
},
$matches[0]
);
print_r($matches);
我想要 preg_match_all
到 return 它找到的所有模式,即使结果已经被使用。下面的示例隔离了问题。
$str = "whatever aaa 34567 aaa 56789 ll";
$pattern = '/.{0,100}\D[aaa]{3}\D{1}[0-9]{5}\D{1}/';
preg_match_all($pattern, $str, $amatches);
var_dump($amatches);
以上return个数组元素的结果。
0=> `whatever aaa 34567 aaa 56789 `
我要的是2个数组元素。
0=> `whatever aaa 34567`
1=> `whatever aaa 34567 aaa 56789`
这个更近一点:
$str = "whatever aaa 34567 aaa 56789 ll";
$pattern = '/^((.*)\D[aaa]{3}\D{1}[0-9]{5}\D{1})?/';
preg_match($pattern, $str, $amatches);
var_dump($amatches);
returns
array(3) {
[0] => string(29) "whatever aaa 34567 aaa 56789 "
[1] => string(29) "whatever aaa 34567 aaa 56789 "
[2] => string(18) "whatever aaa 34567"
}
或者这仍然使用 preg_match_all:
$str = "whatever aaa 34567 aaa 56789 ll";
$pattern = '/^((.*)\D[aaa]{3}\D{1}[0-9]{5}\D{1})?/';
preg_match_all($pattern, $str, $amatches);
var_dump($amatches);
我认为正在发生的事情是您的 .{0,100} 正在被通读整个内容,而根本不允许正则表达式在最后启动。这 ?确保它以您的模式结尾。
这是使用 preg_replace_callback 完成这项工作的替代解决方案。
- 查找匹配 "any characters followed by (and including) three 'a' characters, some space and five digits" 的字符串。可能有尾随空格。
\b
表示单词边界,防止匹配 "xaaa 12345"、"aaa 123456" 或 "aaa 12345xyz" - 将匹配字符串连接到
$soFar
,其中包含任何先前匹配的字符串 - 将该字符串附加到
$result
数组
我不太确定你是否希望 "foo"s 和 "bar"s 保留在字符串中,所以我把它们留在了。
$str = "whatever foo aaa 12345 bar aaa 34567 aaa 56789 baz fez";
preg_replace_callback(
'/.*?\baaa +\d{5}\b\s*/',
function ($matches) use (&$result, &$soFar) {
$soFar .= $matches[0];
$result[] = trim($soFar);
}, $str
);
print_r($result);
输出:
Array
(
[0] => whatever foo aaa 12345
[1] => whatever foo aaa 12345 bar aaa 34567
[2] => whatever foo aaa 12345 bar aaa 34567 aaa 56789
)
使用 preg_match_all and array_map 的两步版本:
preg_match_all('/.*?\baaa +\d{5}\b\s*/', $str, $matches);
$matches = array_map(
function ($match) use (&$soFar) {
$soFar .= $match;
return trim($soFar);
},
$matches[0]
);
print_r($matches);