arrays - Php preg_match with wild card characters
Get the solution ↓↓↓I have some zip code in an array which includes some wild card characters like this
$zip_codes = array( '12556', '765547', '234*', '987*' );
$target_zip = '2347890';
So to check whether the target zip is already present in the array. I am doing like this
foreach( $zip_codes as $zip ) {
if ( preg_match( "/{$target_zip}.*$/i", $zip ) ) {
echo 'matched';
break;
}
else {
echo 'not matched';
}
}
But its not matching the zip at all. Can someone tell me whats the issue here?
Answer
Solution:
One of the problems is that using234*
in a regex will match any number of4
's.
The other problem is that you match to the end (using$
) but not the start, so789
(with the.*
appended) will also match (as it's in the middle). In this code, I use^{$zip}$
, with*
replaced with.*
to match any trailing characters...
$zip_codes = array( '12556', '765547', '789', '234', '234*', '987*' );
$target_zip = '2347890';
foreach( $zip_codes as $zip ) {
$zip = str_replace("*", ".*", $zip);
if ( preg_match( "/^{$zip}$/i", $target_zip ) ) {
echo $zip.' matched'.PHP_EOL;
break;
}
else {
echo $zip.' not matched'.PHP_EOL;
}
}
Answer
Solution:
You don't need regex here.
You can look for*
and based on that look for an exact on the number of characters -1.
$zip_codes = array( '12556', '765547', '234*', '987*' );
$target_zip = '2347890';
foreach($zip_codes as $zip){
if(strpos($zip, "*") !== false){
//if "234* -1 = "234" == substr("2347890",0,3)
if(substr($zip, 0, -1) == substr($target_zip, 0, strlen($zip)-1)){
echo "wildcard match";
}
}else{
if($zip == $target_zip){
echo "excat match";
}
}
}
Answer
Solution:
You need to turn your$zip
values into valid regular expressions by converting*
into.*
(or perhaps\d*
); then you can test them against$target_zip
:
$zip_codes = array( '12556', '765547', '234*', '987*' );
$target_zip = '2347890';
foreach( $zip_codes as $zip ) {
echo $zip;
if (preg_match('/' . str_replace('*', '.*', $zip) . '/', $target_zip)) {
echo ' matched'. PHP_EOL;
break;
}
else {
echo ' not matched' . PHP_EOL;
}
}
Output:
12556 not matched
765547 not matched
234* matched
You haven't indicated whether you want the value in$zip_codes
to match the entire$target_zip
value or just part of it. The code above will work for just part (i.e.234
will match12345
); if you don't want that, change the regex construction to:
if (preg_match('/^' . str_replace('*', '.*', $zip) . '$/', $target_zip)) {
The anchors will ensure that$zip
matches the entirety of$target_zip
.
Answer
Solution:
The issue is that in the loop, the pattern is always the same:
if ( preg_match( "/2347890.*$/i", $zip ) ) {
I think you meant to use the value of$zip
as part of the pattern, which causes the issue repeating the last digit 0+ times in:
if ( preg_match( "/234*.*$/i", $zip ) ) {
^^
As an alternative, you could also extract the digits from$zip_codes
using a capturing group and match optional following*
^(\d+)\**$
Then use strpos to check if thetarget_zip
start with the extracted digits.
$zip_codes = array( '12556', '765547', '234*', '987*', '237' );
$target_zip = '2347890';
foreach($zip_codes as $zip ) {
$digitsOnly = preg_replace("~^(\d+)\**$~", "$1", $zip);
if (strpos($target_zip, $digitsOnly) === 0) {
echo "$zip matched $target_zip" . PHP_EOL;
break;
}
else {
echo "$zip not matched $target_zip" . PHP_EOL;
}
}
Output
12556 not matched 2347890
765547 not matched 2347890
234* matched 2347890
Share solution ↓
Additional Information:
Link To Answer People are also looking for solutions of the problem: the requested url was not found on this server. xampp
Didn't find the answer?
Our community is visited by hundreds of web development professionals every day. Ask your question and get a quick answer for free.
Similar questions
Find the answer in similar questions on our website.
Write quick answer
Do you know the answer to this question? Write a quick response to it. With your help, we will make our community stronger.