Вопрос по битовым операциям + африметика, почему 4 + 2 = 0?

ПашаV

Новичок
В одном из вопросов в тесте Zend PHP5.3 встретился такой вопрос, хоть убейте не понимаю как формируется ответ:

What is the output code?
PHP:
<?php
  if ( (5&6+1) == (5&(6+1)) ) {
     echo 'Успех';
  } else {
     echo 'Провал';
  }
?>

Тут невооруженным взглядом видно, что обе части не равны, т.к. скобки дают различный приоритет операциям (побитовое И и сложение), я мыслил так:

5 = 0101
6 = 0110
7 = 0111

1) Вычисляем выражение 1 (5&6+1):
PHP:
0101 = 5
0110 = 6
=
0100 = 4

Далее 4 + 1 = 5

2) Вычисляем выражение 2 (5&(6+1)):

6+1 = 7

PHP:
0101 = 5
0111 = 7
=
0101 = 5

Из чего я решаю изменить своё решение и ставлю первый вариант: Успех.

Но следом за этим вопросом идет другой, аналогичный но с другими цифрами, а именно "+1" меняется на "+2", ну я с дуру отвечаю также (радуясь что система тестирования случайно дала дважды аналогичный вопрос), но потом решаю пересчитать, и получаю следующее:

1) Вычисляю 5&6+2:
PHP:
0101 = 5
0110 = 6
=
0100 = 4

4 + 2 = 6

2) Вычисляю 5&(6+2):

6+2 = 8 (1000)

PHP:
0101 = 5
1000 = 8
=
0

Т.е. Выражения 5&6+2 и 5&(6+2) НЕ РАВНЫ!!!!

Но если бы загвоздка заключалась именно в этом, на самом деле они равны, т.к. если запустить в PHP этот код:
PHP:
<?
echo 5&6+2;
echo 5&(6+2);
?>

мы в обоих случаях получаем 0 (ноль), причем когда я стал вникать в это написал следующий небольшой код демонсттирующий расчеты:

PHP:
<?
for ($i = 0; $i <= 20; $i++) {
   echo '' . (5&6+$i) . ' = ' . (5&(6+$i)) . '<br>';
}
?>

и вот результат кода:

PHP:
 4 = 4
 5 = 5
 0 = 0
 1 = 1
 0 = 0
 1 = 1
 4 = 4
 5 = 5
 4 = 4
 5 = 5
 0 = 0
 1 = 1
 0 = 0
 1 = 1
 4 = 4
 5 = 5
 4 = 4
 5 = 5
 0 = 0
 1 = 1
 0 = 0

После чего мой мозг окончательно умер, когда я стал разбираться почему

5&6+4 тоже самое что и 5&6+10, сначала я думал что всё дело в четности или нечетности прибавляемого $i, но 5&6+6 = 4, т.е. и тут непонятно.

У кого нибудь есть идеи что это вообще такая за арифметика в PHP и есть ли этому нормальное объяснение, т.к. на php.net/manual/ru - я ничего не могу найти по этой теме, равно как и в Гугле и других системах.

Заранее спасибо!
 
Ты очень много написал, я в самом начале вижу, что не учитываешь, что у оператора «+» приоритет выше, чем у «&»: http://php.net/manual/en/language.operators.precedence.php

Да, спасибо теперь понятно, я думал что побитовое и на одном или большем уровене со сложением находится, а теперь ясно, пересчитал всё выше приведенное и понял что действительно так.

Значит все выражения типа

PHP:
(5&6+1) == (5&(6+1))

всегда равны между собой, т.к. это одно и тоже.
 
вывод,

количество различных результатов выражения X&N (где N - любое целое число) всегда равно всем возможным комбинациям двоичного представления числа X.

Пример:
X = 5 = 0101;
у двоичного представления числа 5 (всего четыре возможные комбинации):
0000 = 0, 0001 = 1, 0100 = 4, 0101 = 5

Поэтому результаты кода, не будут выходить за рамки возможных значений (0,1,4,5)

PHP:
<?
for ($i = 0; $i <= 20; $i++) {
   echo 5 & $i;
}
?>

ответы:
PHP:
010145450101454501014
 
Забавно, но вот эти вещи (обе) выводят друг за другом числа от 1 до 10

PHP:
<?
for ($i = 1; $i <= 10; $i++) {
      echo (15&$i) . '';
}
        
echo '<br>';
       
for ($i = 1; $i <= 10; $i++) {
       echo $i;
}
?>

Т.е. любое целое число N в результате побитового И (&) с числом 15 возвращает само себя, пока не превысит само число 15, далее результат непредсказуем (факт)
 
Забавно, но аналогично ведут себя числа 31, 63, и т.д.!

Может дело в том, что в двоичном представлении они состоят из единиц?
 
Сверху