Что такое &&& операция в C


195
#include <stdio.h>

volatile int i;

int main()
{
    int c;

    for (i = 0; i < 3; i++) 
    {
         c = i &&& i;
         printf("%d\n", c);
    }

    return 0;
}

Выход вышеуказанной программы составлен с использованием gccв

0
1
1

С опцией -Wallили выдает предупреждение:-Waddressgcc

warning: the address of ‘i’ will always evaluate as ‘true’ [-Waddress]

Как cоценивается в вышеуказанной программе?


42
Я верю, что это i && (&i)? Интересно, что я не могу найти повторяющийся пост на SO.
— irrelephant

42
while (i &&& i <-- j) {},
— Кеннитм


8
Не дубликат, но похожий вопрос, и это хорошая ссылка
— Натан Купер

Ответы:


272

Это c = i && (&i);, со второй частью, излишней, так &iкак никогда не будет оценивать false.

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

Если вы включите предупреждения , вы получите что-то вроде:

предупреждение: адрес 'i' всегда будет оцениваться как 'true'


1
Почему бы и нет c = i & (&&i);; Где iкакой-то ярлык?
— Anishsane

4
@anishsane iопределяется как intи в вопросе нет меток. Кроме того, максимальный
— хруст

5
@anishsane: И &&оператор для получения адреса метки в любом случае является нестандартным расширением gcc. Но даже если бы оно было стандартным, правило максимального значения munch не позволило бы выполнить его анализ таким образом (если вы не вставите пробел).
— Кит Томпсон

На самом деле, &iможете оценить false. Его используют иногда по умолчанию. Пример: void fn(type& x = *reinterpret_cast<type*>(NULL)); какое значение &xв fnif fnвызывается без параметров? Это 0 ака ложь. Однако, используя описанный способ, это всегда будет верно, если i == 0, и если бы кто-то использовал его, как я описал, это было бы так c = &i && i.
— Адриан

@LuchianGrigore: как так?
— Адриан

118

В &&&Си нет оператора или токена. Но операторы &&(логические «и») и &(унарный адрес или побитовый «и») существуют.

По правилу максимального жаворонка это:

c = i &&& i;

эквивалентно этому:

c = i && & i;

Устанавливается cв 1, если оба iи &iистинны, и в 0, если любой из них ложен.

Для типа int любое ненулевое значение имеет значение true. Для указателя любое ненулевое значение является истинным (а адрес объекта всегда ненулевым). Так:

Он устанавливается cв 1, если iне равен нулю, или в 0случае, если iравен нулю.

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

c = i && 1;
c = !!i;
c = (bool)i;          // C++ or C with <stdbool.h>
c = i ? 1 : 0;        /* C */
c = i ? true : false; // C++
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.