Page 590 - Beginning PHP 5.3
P. 590
Part III: Using PHP in Practice
If you prefer, you can have preg_match_all() swap the indices around so that the first index
represents the match number and the second index represents the subpattern number. (You might find
the array easier to work with this way around.) To do this, pass the flag PREG_SET_ORDER as the fourth
argument to preg_match_all() :
$scores = “John: 143 points, Anna: 175 points, and Nicole: 119 points”;
preg_match_all( “/(\w+)\:\s(\d+) points/”, $scores, $matches, PREG_SET_ORDER
);
echo $matches[0][0] . “ < br / > ”; // Displays “John: 143 points”
echo $matches[1][0] . “ < br / > ”; // Displays “Anna: 175 points”
echo $matches[2][0] . “ < br / > ”; // Displays “Nicole: 119 points”
// The following code displays:
//
// John scored 143
// Anna scored 175
// Nicole scored 119
echo $matches[0][1] . “ scored “ . $matches[0][2] . “ < br / > ”;
echo $matches[1][1] . “ scored “ . $matches[1][2] . “ < br / > ”;
echo $matches[2][1] . “ scored “ . $matches[2][2] . “ < br / > ”;
Notice how the nesting of the array elements has been reversed. Each top - level element in the matches
array is a now a nested array containing the full matched string as element number 0, and each
subpattern match as elements 1 and 2.
As with preg_match() , you an also pass the PREG_OFFSET_CAPTURE flag to access the position of each
match (or subpattern match) in the target string. This causes each match to be returned as a two - element
nested array (rather than a string), with the first element being the matched text and the second element being
the offset. The end result is that the matches array contains three levels of nesting: the subpattern number
(or zero for the whole pattern), then the match number, then the matched text and offset. For example:
$scores = “John: 143 points, Anna: 175 points, and Nicole: 119 points”;
preg_match_all( “/(\w+)\:\s(\d+) points/”, $scores, $matches,
PREG_OFFSET_CAPTURE );
// The following code displays:
//
// John: 143 points (position: 0)
// Anna: 175 points (position: 18)
// Nicole: 119 points (position: 40)
echo $matches[0][0][0] . “ (position: “ . $matches[0][0][1] . “) < br / > ”;
echo $matches[0][1][0] . “ (position: “ . $matches[0][1][1] . “) < br / > ”;
echo $matches[0][2][0] . “ (position: “ . $matches[0][2][1] . “) < br / > ”;
You can combine PREG_SET_ORDER and PREG_OFFSET_CAPTURE as follows:
preg_match_all( “/(\w+)\:\s(\d+) points/”, $scores, $matches, PREG_SET_ORDER
| PREG_OFFSET_CAPTURE );
In this case, the top level of the matches array will contain the match number, the second level will
contain the subpattern number, and the third level will contain the matched text and offset.
552
9/21/09 6:17:55 PM
c18.indd 552
c18.indd 552 9/21/09 6:17:55 PM