Как отключить некоторые биты при игнорировании других, используя только побитовые операторы

Я искал это, но мои результаты были неудовлетворительными, вероятно, из-за того, насколько сложно говорить. У меня есть один объект state, который является byte, который представляет, какие части моего объекта должны быть визуализированы при наблюдении, и метод disableParts(byte partsToDisable), который отключит все биты в state, которые включены в partsToDisable. Как достичь этой функциональности в побитовых операциях? (то есть, используя только AND, OR, XOR, NOT, LSHIFT, ARSHIFT, LRSHIFT, PLUS, MINUS, MULTIPLY и/или DIVIDE и базовые программные функции, такие как циклы и выражения ветвления)

Для немного ясности здесь представлено визуальное представление моей желаемой функциональности:

  0010 0101 (current state, 37 in this example)
? 1010 0010 (bits to disable, -94 in this example)
============
  0000 0101 (new state, 5 in this example)

и фиктивный класс (на Java, так как я думаю, но решение может быть любым языком или псевдокодом):

class BitThoughts
{
  byte state;

  public void doIt()
  {
    state = 0b00100101;
    System.out.println("Initial state: " + state);

    disableParts(0b10100010);

    if (state == 0b00000101)
      System.out.println("Success! New state is " + state);
    else
      System.out.println("Failure! New state is " + state);
  }

  public void disableParts(byte partsToDisable)
  {
    //Do magic to state
  }
}

Ответ


Просто так никто не дергает так сильно, как я... вот ответ:

   0010 0101 (current state, 37 in this example)
& ~1010 0010 (bits to disable, -94 in this example)
=============

becomes:

   0010 0101 (current state: 37)
&  0101 1101 (inverted bits to disable: 93)
=============
   0000 0101 (new state, 5 in this example)

и решение в Java:

public void disableParts(byte partsToDisable)
{
  state &= ~partsToDisable;
}

Ответ 1

Что вам нужно сделать, это инвертировать биты (побитовое НЕ) в partsToDisable, чтобы вы закончили с маской, где 1 - это биты, которые нужно оставить в покое, а 0 - это биты, которые нужно отключить. Затем И эта маска со значением состояния.

public void disableParts( byte partsToDisable)
{
    state = state & (~partsToDisable);
}

Ответ 2

Если вы просто инвертируете биты частей, вы можете просто И это с состоянием

 void disableParts(byte parts) {
     byte invertOfParts = 0b11111111 - parts;
     state &= invertOfParts
 }