Reputation: 167
I need to check if a string contains illegal character and I was wondering if there is a way to do it through an array because I have an array character that are allowed. This is in PHP
The array just in case you want to see it:
$MsgAry1 = array("A","B","C","D","E","F","G","H","I","J",
"K","L","M","N","O","P","Q","R","S","T",
"U","V","W","X","Y","Z","a","b","c","d",
"e","f","g","h","i","j","k","l","m","n",
"o","p","q","r","s","t","u","v","w","x",
"y","z","1","2","3","4","5","6","7","8",
"9","0",".",",","'","?","!"," ","_","-");
Thanks for any help.
Upvotes: 0
Views: 6978
Reputation: 47874
You don't need to loop ...but if you did use a loop, then you'd better use an early return
/break
so that you aren't doing unnecessary iterations after you've found a disqualifying character.
In a project of my own, I'd prefer to store the regex expression instead of an array of characters -- it's just more concise and direct.
If you must an array of characters, you can avoid the explode and loop by trimming all of the safe characters and check if any characters remain after trimming.
Code: (Demo)
$MsgAry1 = ["A","B","C","D","E","F","G","H","I","J",
"K","L","M","N","O","P","Q","R","S","T",
"U","V","W","X","Y","Z","a","b","c","d",
"e","f","g","h","i","j","k","l","m","n",
"o","p","q","r","s","t","u","v","w","x",
"y","z","1","2","3","4","5","6","7","8",
"9","0",".",",","'","?","!"," ","_","-"];
$strings = [
'test',
'1234',
'w0ws3r!',
'##tag##',
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789.,'?! _-"
];
foreach ($strings as $string) {
echo "$string match: " . var_export(!preg_match("~[^\w.,'?! -]~", $string), true) . "\n";
echo "$string ltrim: " . var_export(!strlen(ltrim($string, implode($MsgAry1))), true) . "\n";
echo "$string after trim: \"" . ltrim($string, "A..Za..z0..9.,'?! _-") . "\"\n---\n";
}
Output:
test match: true
test ltrim: true
test after trim: ""
---
1234 match: true
1234 ltrim: true
1234 after trim: ""
---
w0ws3r! match: true
w0ws3r! ltrim: true
w0ws3r! after trim: ""
---
##tag## match: false
##tag## ltrim: false
##tag## after trim: "##tag##"
---
ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789.,'?! _- match: true
ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789.,'?! _- ltrim: true
ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789.,'?! _- after trim: ""
---
!strlen(ltrim($string, "A..Za..z0..9.,'?! _-"))
demonstrates that you can use multiple character ranges in the "character mask" parameter so long as you use ..
to indicate each range. I believe this is the most concise, non-regex technique. Again, if the trimmed string has length, then at least one bad character was found.
No matter which technique you prefer, I strongly discourage iterated calls of in_array()
-- the performance cost will balloon as the length of the input string increases.
Upvotes: 0
Reputation: 580
Here's a non-iterative method, which should perform faster than the existing answers that loop.
function containsIllegalChars($testString) {
static $MsgAry1 = array("A","B","C","D","E","F","G","H","I","J",
"K","L","M","N","O","P","Q","R","S","T",
"U","V","W","X","Y","Z","a","b","c","d",
"e","f","g","h","i","j","k","l","m","n",
"o","p","q","r","s","t","u","v","w","x",
"y","z","1","2","3","4","5","6","7","8",
"9","0",".",",","'","?","!"," ","_","-");
$foundCount = 0;
str_replace($MsgAry1, '', $testString, $foundCount);
return $foundCount > 0;
}
You can make it even more efficient with your specific set of letters by removing all the uppercase letters, and using str_ireplace.
function containsIllegalChars($testString) {
static $MsgAry1 = array("a","b","c","d",
"e","f","g","h","i","j","k","l","m","n",
"o","p","q","r","s","t","u","v","w","x",
"y","z","1","2","3","4","5","6","7","8",
"9","0",".",",","'","?","!"," ","_","-");
$foundCount = 0;
str_ireplace($MsgAry1, '', $testString, $foundCount);
return $foundCount > 0;
}
Upvotes: 3
Reputation: 661
You can use the str_split
and in_array
functions to do this, as thus:
$MsgAry1 = array("A","B","C"); //Add your actual array here
$testCase = "Hello, World!";
$testCase_arr = str_split($testCase);
foreach($testCase as $test)
{
if(!in_array($test, $MsgAry1))
{
echo "Error! Invalid Character!";
break(); //Or exit();, as needed
}
}
Upvotes: 5
Reputation: 2363
$resultarray = preg_replace("/[^A-Za-z0-9]/", "", $MsgAry1);
print_r ($resultarray);
Upvotes: 2
Reputation: 14590
You could use something like this, str_split
splits the string into characters then you can check each one with in_array
:
$MsgAry1 = array("A","B","C","D","E","F","G","H","I","J",
"K","L","M","N","O","P","Q","R","S","T",
"U","V","W","X","Y","Z","a","b","c","d",
"e","f","g","h","i","j","k","l","m","n",
"o","p","q","r","s","t","u","v","w","x",
"y","z","1","2","3","4","5","6","7","8",
"9","0",".",",","'","?","!"," ","_","-");
$string = "Hello";
foreach (str_split($string) as $char) {
if (in_array($char, $MsgAry1)) {
echo "Char: ".$char." -> OK";
} else {
echo "Char: ".$char." -> KO";
}
}
Upvotes: 2