Понимание PHP Тип принуждения

Я видел этот небольшой фрагмент кода, который уклоняется от моего понимания:

<?php

$a = '0e462097431906509019562988736854';
$b = '0e830400451993494058024219903391';

var_dump($a == $b);

Который будет выводить:

bool(true)

Я понимаю что при использовании == PHP попытается выполнить нечеткое сравнение, тихо конвертируя между типами, чтобы выполнить сравнение. Что я не Понимание — почему PHP, кажется, думает, что эти две строки одинаковы. Я бы подумал с $a а также $b являются строками, что преобразование типов не требуется.

Что я не понимаю?

7

Решение

Я думаю, что эта статья объясняет это довольно хорошо:

Операторы сравнения приведения типов преобразуют числовые строки в числа

Просто процитирую основной вопрос здесь:

В соответствии с php language.operators.comparison, операторы сравнения приведения типов приведут оба операнда к плавающим, если они оба будут выглядеть как числа, даже если они оба уже являются строками:

где оба strings используют экспоненциальную запись, поэтому обрабатываются как числовые строки, что делает свободное сравнение (==), приведите эти strings в floats прежде чем на самом деле «слабо» сравнивать их.

В качестве лучшей практики и для предотвращения непредвиденного поведения всегда старайтесь использовать равенство идентичности (===), особенно когда имеешь дело с strings

7

Другие решения

PHP пытается преобразовать в тип float, потому что строка начинается с 0. Она останавливается после 0, потому что следующий символ не является числом. То же самое происходит, когда вы используете приведение типов для преобразования научной нотации в целое число:

$x = (float)"12E-1x";  // $x == 1.2
$x = (int)"12E-1x";  // $x == 12 (stops at E because it's not an integer)
1

Это не совсем ответ, но если вы попробуете:

$a = '0e4620974319065090195629887368549';
$b = '0e8304004519934940580242199033918';
echo floatval($a) . '<br>' . floatval($b);var_dump($a == $b);

Ты получаешь:

0

0

BOOL (истина)

Теперь, если вы попробуете:

$a = '0e4620974319065090195629887368549';
$b = '1e8304004519934940580242199033918';
echo floatval($a) . '<br>' . floatval($b);var_dump($a == $b);

Ты получаешь:

0

INF

BOOL (ложь)

Я предполагаю, что PHP преобразует строки в числа с плавающей точкой и выдает результат сравнения, используя полученные значения с плавающей точкой, что в любом случае неверно, но это уже другая история.

0

В официальной документации проверка на равенство между двумя переменными производится следующим образом:

$a == $b # Equal TRUE if $a is equal to $b after type juggling.

Пример :

$a = 13;   # integer type
$b = "13"; # string type
var_dump($a == $b); # will say TRUE, because juggling was made
var_dump($a === $b); # will say FALSE, because PHP will also evaluate the type of variables :)
0
По вопросам рекламы [email protected]