"Hej, Amigo!"

"Jag skulle också vilja prata om bitmasker och XOR."

"Du vet redan att siffror består av bitar och du kan utföra olika operationer på dessa bitar. En bitmask är en representation av flera olika logiska värden (santa/falska värden) som ett enda heltal. I det här fallet motsvarar varje booleskt värde en specifik bit. Så här kan detta göras:"

"Den binära representationen av två potenser (1, 2, 4, 8, 16, 32, ...) innebär bara att sätta en bit:"

siffra Binär representation
1 0000 0001
2 0000 0010
4 0000 0100
8 0000 1000
16 0001 0000
19 (inte en tvåpotens) 0001 0011
31 (inte en tvåpotens) 0001 1111

"Så, vilket heltal som helst kan behandlas som en array av bitar eller en array av booleska värden."

"Så här kan du lagra olika booleska värden i ett nummer:"

booleska värden
boolean a = true;
boolean b = false;
boolean c = true;
boolean d = false;
Värden packade i ett nummer:
int result = 0;
 if (a) result += 1; // 1 == 20 — bit 0
 if (b) result += 2; // 2 == 21 — bit 1
 if (c) result += 4; // 4 == 22 — bit 2
 if (d) result += 8; // 8 == 23 — bit 3

"Nu är varje bit 1 om motsvarande booleska variabel var sann."

I vårt fall var variablerna a och c sanna, så resultatet är lika med 1+4 == 5

0000 0101
0000 dcba

"Jag tror att jag vet vad som händer."

"Tja, om du förstår, låt oss gå vidare."

"En int har 32 bitar. En av dem används för talets tecken, och den andra 31 kan användas för att lagra värdena för 31 booleska variabler."

"En lång har 64 bitar där vi kan lagra 63 booleska variabler."

"Japp."

"Dusintals variabler fullproppade i ett nummer. Det är ganska många."

"Men var tillämpas detta?"

"Främst i situationer där du behöver lagra mycket information om objekt. När du lagrar mycket information om ett objekt, finns det alltid ett par dussin booleska variabler. "Med detta tillvägagångssätt lagras de alla bekvämt i ett nummer ."

"Med betoning på ordet 'lagrat'. För att det faktiskt inte är så bekvämt att använda numret."

"Förresten, det var precis vad jag ville fråga. Hur extraherar vi det booleska värdet från talet?"

"Det är inte alls komplicerat. Låt oss säga att du måste avgöra om bit 6 är satt till 1 (2 i fempotensen är 32). Vi kan kontrollera så här:"

Kombinera siffror till ett:
int a = 32; // 25 == 0010 0000
int b = 8; // 23 == 0000 1000
int c = 2; // 21 == 0000 0010

int result = a + b + c; // 32 + 8 + 2 == 42 == 0010 1010
Extrahera värden genom att kontrollera specifika bitar:
int a = result & 32; // 0010 1010 & 0010 0000 = 0010 0000
int b = result & 8; // 0010 1010 & 0000 1000 = 0000 1000
int c = result & 2; // 0010 1010 & 0000 0010 = 0000 0010

"Att arbeta med bitmasker innebär alltså tre operationer:"

1)  Ställ in en specifik bit till 0

2)  Ställ in en specifik bit till 1

3)  Kontrollera värdet på den specifika biten.

"Ta bit 6, till exempel."

"Hur sätter du bit 6 till 1?"

Koda Beskrivning
result = result | 01000000;
result |= 01000000;
Hur ställer du in bit 6 till 1?
result = result & 10111111;
result &= 10111111;
Hur ställer du in bit 6 till 0?
c = result & 01000000;
Hur får man värdet på bit 6?

"Det är mycket ovanligt, men inte svårt. Man, nu är jag en hot-shot programmerare."

"Och ytterligare ett litet tips om hur man enkelt får siffror med en specifik bit inställd på 0 eller 1: 01000000 eller 10111111."

För detta har vi  operatorerna >> och  << .

"1 är 2 till nollpotens. Med andra ord, ett tal med bit 0 satt till 1. Vi behöver ett tal med bit 6 satt."

int c = 1 << 6; // 0000 0001 << 6 == 0100 0000 == 64

"Coolt! Det är verkligen användbart för sådana fall."

"Men vad händer om jag behöver ett tal där varje bit är satt till 1 utom en specifik bit är satt till 0?"

"Det är inte heller svårt:"

int d = ~(1 << 6); // ~0100 0000 == 10111111

"Med andra ord, det hela är väldigt enkelt:"

Koda Beskrivning
result = result | (1 << 6);
result |= (1 << 6);
Hur ställer du in bit 6 till 1?
result = result & ~(1 << 6);
result &= ~(1 << 6);
Hur ställer du in bit 6 till 0?
c = result & (1 << 6);
Hur får man värdet på bit 6?

"Det ser inte särskilt svårt ut. Men jag kommer inte ihåg det direkt."

"Men om du stöter på ett skrämmande uttryck som "resultat &= ~(1 << 6)" i någon annans kod, kommer du att veta att den här personen bara arbetar med en bitmask."

"Och om du stöter på det ofta, kommer det att komma ihåg sig självt för dig."

"Kom ihåg sig själv... Det låter bra. Tack för lektionen."