PHP preg_match_all 谜语
PHP preg_match_all riddle
我正在使用 PHP 5.6 版,但我无法弄清楚为什么正则表达式无法正确匹配第二行。
$str = '<tr><td class="DH">Sale Date</td></tr><tr><td class="DD">10-MAR-15</td></tr><tr><td class="DD">18-APR-17</td></tr>';
preg_match_all('/<tr>.*?class="D.*?<\/tr>/', $str, $matches);
print_r($matches);
preg_match_all('/<tr>.*?class="DH.*?<\/tr>/', $str, $matches);
print_r($matches);
preg_match_all('/<tr>.*?class="DD.*?<\/tr>/', $str, $matches);
print_r($matches);
此代码输出:
Array
(
[0] => Array
(
[0] => <tr><td class="DH">Sale Date</td></tr>
[1] => <tr><td class="DD">10-MAR-15</td></tr>
[2] => <tr><td class="DD">18-APR-17</td></tr>
)
)
Array
(
[0] => Array
(
[0] => <tr><td class="DH">Sale Date</td></tr>
)
)
Array
(
[0] => Array
(
[0] => <tr><td class="DH">Sale Date</td></tr><tr><td class="DD">10-MAR-15</td></tr>
[1] => <tr><td class="DD">18-APR-17</td></tr>
)
)
正则表达式本质上意味着匹配所有最短的序列
<tr>
和 </tr>
包含 class="D
。
注意第一个正则表达式如何分别正确匹配所有 3 行。
第二个做同样的事情,但希望该行包含 class="DH
它正确地做。
第三个正则表达式应该匹配包含 class="DD
的其他行。出于某种原因,只有第一个结果(对应于第二个 table 行)想要包含上一行。
即使我在 </tr>
和 <tr>
之间添加 space,就像在 </tr> <tr>
中一样,我也会得到相同的结果。但是,如果我插入一个换行符,事情就会起作用。
任何人都可以解释发生了什么以及如何修复我的代码吗?
/<tr>.*?class="DD.*?/
说“找到 <tr>
,然后匹配 所有内容 直到找到 class="DD"
。所以它看到:
<tr><td class="DH">Sale Date</td></tr><tr><td class="DD">
并匹配第一个 <tr>
,然后 .*
匹配 <td class="DH">Sale Date</td></tr><tr><td
,然后它看到匹配下一部分的 class="DH"
。
当您添加换行符时,.*
停止匹配,因此它可以正常工作。
我正在使用 PHP 5.6 版,但我无法弄清楚为什么正则表达式无法正确匹配第二行。
$str = '<tr><td class="DH">Sale Date</td></tr><tr><td class="DD">10-MAR-15</td></tr><tr><td class="DD">18-APR-17</td></tr>';
preg_match_all('/<tr>.*?class="D.*?<\/tr>/', $str, $matches);
print_r($matches);
preg_match_all('/<tr>.*?class="DH.*?<\/tr>/', $str, $matches);
print_r($matches);
preg_match_all('/<tr>.*?class="DD.*?<\/tr>/', $str, $matches);
print_r($matches);
此代码输出:
Array
(
[0] => Array
(
[0] => <tr><td class="DH">Sale Date</td></tr>
[1] => <tr><td class="DD">10-MAR-15</td></tr>
[2] => <tr><td class="DD">18-APR-17</td></tr>
)
)
Array
(
[0] => Array
(
[0] => <tr><td class="DH">Sale Date</td></tr>
)
)
Array
(
[0] => Array
(
[0] => <tr><td class="DH">Sale Date</td></tr><tr><td class="DD">10-MAR-15</td></tr>
[1] => <tr><td class="DD">18-APR-17</td></tr>
)
)
正则表达式本质上意味着匹配所有最短的序列
<tr>
和 </tr>
包含 class="D
。
注意第一个正则表达式如何分别正确匹配所有 3 行。
第二个做同样的事情,但希望该行包含 class="DH
它正确地做。
第三个正则表达式应该匹配包含 class="DD
的其他行。出于某种原因,只有第一个结果(对应于第二个 table 行)想要包含上一行。
即使我在 </tr>
和 <tr>
之间添加 space,就像在 </tr> <tr>
中一样,我也会得到相同的结果。但是,如果我插入一个换行符,事情就会起作用。
任何人都可以解释发生了什么以及如何修复我的代码吗?
/<tr>.*?class="DD.*?/
说“找到 <tr>
,然后匹配 所有内容 直到找到 class="DD"
。所以它看到:
<tr><td class="DH">Sale Date</td></tr><tr><td class="DD">
并匹配第一个 <tr>
,然后 .*
匹配 <td class="DH">Sale Date</td></tr><tr><td
,然后它看到匹配下一部分的 class="DH"
。
当您添加换行符时,.*
停止匹配,因此它可以正常工作。