Compare two digits elegant solution - php

I have the following two variables:
$addressphone='5612719999';
$googlephone='561-271-9999';
Is there an elegant solution in PHP that can validate that these two variables actually are equal. I'd prefer not to use str_replace as the conditions can change and I'd have to account for everything.
I've tried casting and intval but neither seemed to work
UPDATE
$addressphone='5612719999';
$googlephone='561-271-9999';
preg_replace("/\D/","",$googlephone);
var_dump($googlephone);
returns string(12) "561-271-9999"

I'm kind of reiterating what the comments say, but you should remove the non-digits from each string and them compare their integer values.
// original, non-integer-infested strings
$addressphone= "5612719999";
$googlephone= "561-271-9999";
// remove non-digits
$addressphone = preg_replace("/\D/","",$addressphone);
$googlephone = preg_replace("/\D/","",$googlephone);
and then you can check the following condition for equality:
// compare integer values of digit-only strings
intval($addressphone) == intval($googlephone)
// should return true

I would use preg_replace() to remove all non-numeric characters. That way, you're just working with numeric strings, which you can compare any way you'd like.
<?php
$testString = "123-456-7890";
echo preg_replace("/\D/", "", $testString); //echos 1234567890
?>

Try this :
print_r($addressphone === implode("", explode("-",$googlephone)))

$pieces = explode("-", $googlephone);
$newstring="";
foeach ($piece in $pieces)
{
$newstring +=piece;
}
Now compare your string with $newstring.

Remove everything that isn't a digit:
<?php
$addressphone ='5612719999';
$googlephone ='561-271-9999';
$number_wang = function($numberish) {
return preg_replace('/[^0-9]/', '', $numberish);
};
assert($number_wang($googlephone) == $addressphone);

Related

PHP - Check for leading 0's in 2 comma-delimited integers

I have a user-input string with 2 comma-delimited integers.
Example (OK):
3,5
I want to reject any user input that contains leading 0's for either number.
Examples (Bad):
03,5
00005,3
05,003
Now what I could do is separate the two numbers into 2 separate string's and use ltrim on each one, then see if they have changed from before ltrim was executed:
$string = "03,5";
$string_arr = explode(",",$string);
$string_orig1 = $string_arr[0];
$string_orig2 = $string_arr[1];
$string_mod1 = ltrim($string_orig1, '0');
$string_mod2 = ltrim($string_orig2, '0');
if (($string_mod1 !== $string_orig1) || ($string_mod2 !== $string_orig2)){
// One of them had leading zeros!
}
..but this seems unnecessarily verbose. Is there a cleaner way to do this? Perhaps with preg_match?
You could shorten the code and check if the first character of each part is a zero:
$string = "03,5";
$string_arr = explode(",",$string);
if ($string_arr[0][0] === "0" || $string_arr[1][0] === "0") {
echo "not valid";
} else {
echo "valid";
}
Here is one approach using preg_match. We can try matching for the pattern:
\b0\d+
The \b would match either the start of the string, or a preceding comma separator.
If we find such a match, it means that we found one or more numbers in the CSV list (or a single number, if only one number present) which had a leading zero.
$input = "00005,3";
if (preg_match("/\b0\d+/", $input)) {
echo "no match";
}
You can do a simple check that if the first character is 0 (using [0]) or that ,0 exists in the string
if ( $string[0] == "0" || strpos($string, ",0") !== false ) {
// One of them had leading zeros!
}
All the current answers fail if any of the values are simply 0.
You can just convert to integer and back and compare the result.
$arr = explode(',', $input);
foreach($arr as $item) {
if( (str)intval($item) !== $item ) {
oh_noes();
}
}
However I am more curious as to why this check matters at all.
One way would be with /^([1-9]+),(\d+)/; a regex that checks the string starts with one or more non-zero digits, followed by a comma, then one or more digits.
preg_match('/^([1-9]+),(\d+)/', $input_line, $output_array);
This separates the digits into two groups and explicitly avoids leading zeros.
This can be seen on Regex101 here and PHPLiveRegex here.

Compare two string and ignore (but not replace) accents. PHP

I got (for example) two strings:
$a = "joao";
$b = "joão";
if ( strtoupper($a) == strtoupper($b)) {
echo $b;
}
I want it to be true even tho the accentuation. However I need it to ignore the accentuation instead of replacing because I need it to echo "joão" and not "joao".
All answers I've seen replace "ã" for "a" instead of making the comparison true. I've been reading about normalizing it, but I can't make it work either. Any ideas? Thank you.
Just convert the accents to their non-accented counter part and then compare strings. The function in my answer will remove the accents for you.
function removeAccents($string) {
return strtolower(trim(preg_replace('~[^0-9a-z]+~i', '-', preg_replace('~&([a-z]{1,2})(acute|cedil|circ|grave|lig|orn|ring|slash|th|tilde|uml);~i', '$1', htmlentities($string, ENT_QUOTES, 'UTF-8'))), ' '));
}
$a = "joaoaaeeA";
$b = "joãoâàéèÀ";
var_dump(removeAccents($a) === removeAccents($b));
Output:
bool(true)
Demo
I would like to share an elegant solution that avoids the usage of htmlentities and that doesn't need to manually list all chars replacements. It is the traduction in php of the answers to this post.
function removeAccents($str) {
return preg_replace('/[\x{0300}-\x{036f}]/u',"",normalizer_normalize($str,Normalizer::FORM_D));
}
$a = "joaoaaeeA";
$b = "joãoâàéèÀ";
var_dump(removeAccents($a) === removeAccents($b));
Output:
bool(true)
It's not a plain PHP solution but works very well for this situation, run this query on MySQL:
SELECT 'joão' = 'joao'
So if you have access to mysql you can use it from PHP.

PHP : Get a number between 2 strings

I have this string:
a:3:{i:0;i:2;i:1;i:3;i:2;i:4;}
I want to get number between "a:" and ":{" that is "3".
I try to user substr and strpos but no success.
I'm newbie in regex , write this :
preg_match('/a:(.+?):{/', $v);
But its return me 1.
Thanks for any tips.
preg_match returns the number of matches, in your case 1 match.
To get the matches themselves, use the third parameter:
$matches = array();
preg_match(/'a:(\d+?):{/', $v, $matches);
That said, I think the string looks like a serialized array which you could deserialize with unserialize and then use count on the actual array (i.e. $a = count(unserialize($v));). Be careful with userprovided serialized strings though …
If you know that a: is always at the beginning of the string, the easiest way is:
$array = explode( ':', $string, 3 );
$number = $array[1];
You can use sscanfDocs to obtain the number from the string:
# Input:
$str = 'a:3:{i:0;i:2;i:1;i:3;i:2;i:4;}';
# Code:
sscanf($str, 'a:%d:', $number);
# Output:
echo $number; # 3
This is often more simple than using preg_match when you'd like to obtain a specific value from a string that follows a pattern.
preg_match() returns the number of times it finds a match, that's why. you need to add a third param. $matches in which it will store the matches.
You were not too far away with strpos() and substr()
$pos_start = strpos($str,'a:')+2;
$pos_end = strpos($str,':{')-2;
$result = substr($str,$pos_start,$pos_end);
preg_match only checks for appearance, it doesn't return any string.

Filter out numbers in a string in php

assuming i have these texts 'x34' , '150px' , '650dpi' , 'e3r4t5' ... how can i get only numbers ? i mean i want 34 , 150 , 650 , 345 without any other character . i mean get the numbers this string has into one variable .
$str = "e3r4t5";
$str_numbers_only = preg_replace("/[^\d]/", "", $str);
// $number = (int) $str;
Sorry for joining the bandwagon late, rather than using Regex, I would suggest you use PHP's built in functions, which may be faster than Regex.
filter_var
flags for the filters
e.g. to get just numbers from the given string
<?php
$a = '!a-b.c3#j+dk9.0$3e8`~]\]2';
$number = str_replace(['+', '-'], '', filter_var($a, FILTER_SANITIZE_NUMBER_INT));
// Output is 390382
?>
To adhere to more strict standards for your question, I have updated my answer to give a better result.
I have added str_replace, as FILTER_SANITIZE_NUMBER_FLOAT or INT flag will not strip + and - chars from the string, because they are part of PHP's exception rule.
Though it has made the filter bit long, but it's now has less chance of failing or giving you unexpected results, and this will be faster than REGEX.
Edit:
1: Realized that with FILTER_SANITIZE_NUMBER_FLOAT, PHP won't strip these characters optionally .,eE, hence to get just pure numbers kindly use FILTER_SANITIZE_NUMBER_INT
2: If you have a PHP version less than 5.4, then kindly use array('+', '-') instead of the short array syntax ['+', '-'].
You can use a regular expression to remove any character that is not a digit:
preg_replace('/\D/', '', $str)
Here the pattern \D describes any character that is not a digit (complement to \d).
Use PHP FILTER functions if you are using PHP 5.2.X, 5.3.x,5.4 . Its highly recommended
$mixed_input = "e3r4t5";
$only_numbers = filter_var($mixed_input, FILTER_SANITIZE_NUMBER_INT);
Please Go through with this link to know more
Replace everything that isn't a number and use that value.
$str = "foo1bar2baz3";
$num = intval(preg_replace("/[^0-9]/", "", $str));
You could use the following function:
function extract_numbers($string) {
preg_match_all('/([\d]+)/', $string, $match);
return $match;
}

PHP - Sanitise a comma separated string

What would be the most efficient way to clean a user input that is a comma separated string made entirely on numbers - e.g
2,40,23,11,55
I use this function on a lot of my inputs
function clean($input){ $input=mysql_real_escape_string(htmlentities($input,ENT_QUOTES)); return $input; }
And on simple integers I do:
if (!filter_var($_POST['var'], FILTER_VALIDATE_INT)) {echo('error - bla bla'); exit;}
So should I explode it and then check every element of the array with the code above or maybe replace all occurrences of ',' with '' and then check the whole thing is a number? What do you guys think?
if (ctype_digit(str_replace(",", "", $input))) {
//all ok. very strict. input can only contain numbers and commas. not even spaces
} else {
//not ok
}
If it is CSV and if there might be spaces around the digits or commas and maybe even some quotation marks better use a regex to check if it matches
if (!preg_match('/\A\d+(,\d+)*\z/', $input)) die('bad input');
If you want to transform a comma-separated list instead of simply rejecting it if it's not formed correctly, you could do it with array_map() and avoid writing an explicit loop.
$sanitized_input = implode(",", array_map("intval", explode(",", $input)));
I would filter instead of error checking on simple input, though only 'cause I'm lazy, I suppose, and usually in a web context there's way too many cases to handle on what could be coming in that I wouldn't expect: Simple filter below.
<?php
$input = '234kljsalkdfj234a,a, asldkfja 345345sd,f jasld,f234l2342323##$##';
function clean($dirty){ // Essentially allows numbers and commas, just strips everything else.
return preg_replace('/[^0-9,]/', "", (string) $dirty);
}
$clean = clean($input);
echo $clean;
// Result: 234234,,345345,,2342342323
// Note how it doesn't deal with adjacent filtered-to-empty commas, though you could handle those in the explode. *shrugs*
?>
Here's the code and the output on codepad:
http://codepad.org/YfSenm9k

Categories