I browsed through several similar questions, but they all only state the fact:
If ... comparison involves numerical strings, then each string is conve
Because, PHP produce a product for End-Users, not for Application Developers. So when you produce such product like below:
if (isset($_POST['submit'])){
if ($_POST['myinput'] == "1") echo 'Yes'; //or == 1
else echo 'NO';
}
?>
<form name="myform" method="POST" action="">
<input name="myinput">
<input name="submit" type="submit">
</form>
If the user enter 1
or 0001
, what do you expect to print in both case? Yes
or NO
?
the answer is clear. we expect to see Yes
. so this is why PHP does so
If for any rare reason, we need to definitely compare them, then we should change ==
to ===
Ah, finally I got it. It was quite stupid of me.
Comparison involves not only "is equal"
but also "less than"
and "greater than"
. And for the latter two it is obviously critical to cast numerical operands before comparison, because numbers often being represented in PHP as strings, and 11 have to be greater than 9 even if both stored in strings.
So, as compare_function() does all the comparisons at once, returns either 1, 0, -1
to tell if first operand is bigger, equal or less than second respectively - well, it's fairly explains, why operands being cast.
You can compare two strings.
"00001" === "1" // false
Remember ==
means equivalent ===
means equal
My only guess as to why this is the case is because in the beginning PHP strived to be a type-less language before they went the route of becoming a loosely typed language.
PHP was originally string processor that allowed for a little scripting inside of it. Since all inputs on the web are textual in nature it had to work hard given textual input to behave sanely when it came to dealing with numbers.
I could be wrong about this but I don't believe the ability to explicitly cast data types entered the stage until PHP 4 with the introduction of the *val functions (like intval) etc. and I think the casting notation, like (int)
came around after that.
For the non comparison operations it was pretty easy because they all have a type associated with them (+ - / * all deal with numbers whereas . deals with strings) so a clear path to how things should be cast in those cases is apparent.
But with equality or equivalence checks between variables then the only way to do that was to treat everything that looked like a number as a number because at the time the only way it could be gotten would be by externally would be as a string and there was no way to make it otherwise.