Як я можу видалити прапор на C?


148

Є змінна, яка містить деякі прапори, і я хочу видалити один з них. Але я не знаю, як її зняти.

Ось як я встановив прапор.

my.emask |= ENABLE_SHOOT;

6
Ви можете знайти відповіді на питання ТА "Як встановити, очистити та переключити один біт на C" корисним.
знімок

Відповіді:


339

Коротка відповідь

Ви хочете виконати побітне І операцію на поточному значенні з операцією Побітовий НЕ прапор, який ви хочете зняти . Побіт НЕ перетворює кожен біт (тобто 0 => 1, 1 => 0).

flags = flags & ~MASK;або flags &= ~MASK;.

Довга відповідь

ENABLE_WALK  = 0    // 00000000
ENABLE_RUN   = 1    // 00000001
ENABLE_SHOOT = 2    // 00000010
ENABLE_SHOOTRUN = 3 // 00000011

value  = ENABLE_RUN     // 00000001
value |= ENABLE_SHOOT   // 00000011 or same as ENABLE_SHOOTRUN

Коли ви виконуєте побітові значення І з побітним значенням НЕ значення, яке ви хочете зняти

value = value & ~ENABLE_SHOOT // 00000001

ви насправді робите:

      0 0 0 0 0 0 1 1     (current value)
   &  1 1 1 1 1 1 0 1     (~ENABLE_SHOOT)
      ---------------
      0 0 0 0 0 0 0 1     (result)

@Aaron: Я радий, що це допомогло. Спочатку у мене були проблеми з розумінням операцій, поки хтось не знадобився 10 хвилин, щоб пояснити це на папері.
Денніс

1
@Dennis Я думав, що XOR буде працювати над видаленням вже встановленого прапора. notification.sound ^= Notification.DEFAULT_SOUND;
likejudo

3
Як увімкнути Walk? Починаючи з X | 0 == X
Unikorn

Як зазначає @Unikorn, значення прапора, яке дорівнює нулю, не працює належним чином, або якщо ви намагаєтесь його АБО чи увімкнено або вимкнете його.
RenniePet

Щоб увімкнути ходьбу, потрібно просто вимкнути запуск (який залишить біт 1 встановлений на 0). Не думайте про прапорці ENABLE_ * як десяткові числа, а як двійкові числа - ні ввімкненими, ні вимкненими. Ви все ще не можете явно дозволити або заборонити ходити , однако.
Якоб Дегелінг


13

Важливо зауважити, що якщо змінна, якою маніпулюється, більше, ніж int, має бути також і значення, яке використовується у виразі 'and not'. Насправді іноді можна піти з використання менших типів, але є достатньо випадкових випадків, що, мабуть, найкраще використовувати суфікси типу, щоб переконатися, що константи є досить великими.


5
+1 для лову неочевидного кутового корпусу. Один із способів уникнути цього - замість цього використовувати flags -= flags & MY_FLAG;(або, ^=якщо вам зручніше).
R .. GitHub СТОП ДОПОМОГАЙТЕ

1
@R .. Я використовував би '^ =', за винятком того, що він перемикає біти, і іноді ви можете не знати, який із багатьох прапорів встановлено. Якщо я хочу переконатися, що два праві біти дорівнюють нулю, наприклад, мій.emask: '0 1 0 1' вхід: '0 0 1 1' з: '^ =' '0 1 1 0' з: '& ~ '' 0 1 0 0 '
Гектор
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.