Hi,
I have filed recent behavior change of == operator as bug #62097
https://bugs.php.net/bug.php?id=62097.
(This is already marked as "Wont fix".)
Changes are:
https://github.com/php/php-src/commit/9344bf193c6e35c8706923953f3e63bb01cc05ed
https://github.com/php/php-src/commit/acd711685a592c52be200e248154283c6c49c9f8
This change is intended to fix Bug #54547 (https://bugs.php.net/bug.php?id=54547).
But there are some backward incompatibility.
I think that this change should not be applied to PHP 5.4.
On PHP, when both operands are strings look like numbers, they are
converted to numbers before comparison, for operator ==, >, <, and others.
(Examples of strings look like numbers are: "123", "-56", "0120", "3.14",
"1E5", "0xff")
Old behavior, if converted numeric value fits into int, it is
evaluated as a int. In other case it is evaluated as a float. (When
zend_finite is false, operand is compared as string. But it is really
rare case.)
But changed new behavior, the case to compare as string is very
extended: Converted number value exceed 2^63-1 in 64 bit, or 2^53-1 in
32-bit environment.
This cause below incompatibility between PHP 5.4.3 and PHP 5.4.4RC2.
var_dump("9223372036854775807" == "9223372036854775808");
// 5.4.3 => bool(true)
// 5.4.4RC2 => bool(false) [Good, fixed]
// leading 0
var_dump("9223372036854775808" == "09223372036854775808");
// 5.4.3 => bool(true)
// 5.4.4RC2 => bool(false) [incompatible]
// leading space
var_dump("9223372036854775808" == " 9223372036854775808");
// 5.4.3 nn => bool(true)
// 5.4.4RC2 => bool(false) [incompatible]
var_dump("12345678901234567890" == "12345678901234567890.0");
// 5.4.3 => bool(true)
// 5.4.4RC2 => bool(false) [incompatible]
var_dump("0xffffffffffffffffff" == "0xFFFFFFFFFFFFFFFFFF");
// 5.4.3 => bool(true)
// 5.4.4RC2 => bool(false) [incompatible]
var_dump("0xffffffffffffffffff" > "0xFFFFFFFFFFFFFFFFFF");
// 5.4.3 => bool(false)
// 5.4.4RC2 => bool(true) [incompatible]
I think any backward incompatible change should not be introduced in
major operators such as ==, anymore. But if behavior change is applied
to string comparison operator, it should be a natural extension of
current behavior; number-like string is compared as number, not as raw
string. (e.g. canonicalize string as number way before string match.)
--
OISHI Kazuo