Этот цикл for возвращает правильное двоичное значение, но добавляет к нему много 0, почему он это делает? - PullRequest
1 голос
/ 12 апреля 2019

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

$dec = 17;

$bin = null;

while($dec != 0)
{
    $bin .= $dec % 2;
    $dec /= 2;
    round($dec, 0, PHP_ROUND_HALF_DOWN);
}

echo $bin;

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

Я пытался проверить на $dec == 0, и если это удастся break;, вот так:

while($dec != 0)
{
    $bin .= $dec % 2;
    $dec /= 2;
    round($dec, 0, PHP_ROUND_HALF_DOWN);
    if($dec == 0)
    {
        break;
    }
}

Это не сработало.Поэтому я ищу решение.Спасибо за помощь в продвижении!Jona

Ответы [ 2 ]

3 голосов
/ 12 апреля 2019

Проблема вашего цикла в том, что $dec /= 2 не является целочисленным делением. Если вы напечатаете $dec в вашем цикле, вы увидите значения 8,5, 4,25, 2,125, ... и так далее, пока в конечном итоге $dec не станет наименьшим возможным значением двойной точности, после чего в следующем цикле оно окончательно становится 0. Хотя вы звоните round, что должно это исправить, вы не назначаете вывод round на $dec, поэтому он не имеет никакого эффекта. Вероятно, предпочтительнее сделать целочисленное деление для начала. В PHP7 и выше вы можете использовать intdiv:

$dec = intdiv($dec, 2);

Или в любой версии PHP работает простой сдвиг вправо:

$dec = $dec >> 1;

В противном случае вы можете использовать intval, floor или round или (int) приведение для преобразования результата с плавающей запятой в целое число:

$dec = intval($dec / 2);
$dec = floor($dec / 2);
$dec = round($dec / 2, 0, PHP_ROUND_HALF_DOWN);
$dec = (int)($dec / 2);

Демонстрация на 3v4l.org

Другая проблема заключается в том, что вам нужно вставить значения в строку $bin в обратном порядке, поэтому вам нужно заменить

$bin .= $dec % 2;

с

$bin = ($dec % 2) . $bin;

Так примерный цикл будет:

$dec = 24;    
$bin = null;
while($dec != 0)
{
    $bin = ($dec % 2) . $bin;
    $dec = $dec >> 1;
}
echo $bin . PHP_EOL;

Выход:

11000
2 голосов
/ 12 апреля 2019

Хорошо, я нашел вашу проблему: если бы вы отладили свой цикл, вы бы увидели, что $dec просто наполовину на каждом шаге.Вызов round ничего не делает, так как вы не используете возвращаемое значение.Просто присвойте это $dec

...