Reputation: 9920
I've used bit masks in Java (not Javascript) before, but it's been a while and it's making me bug out.
This is the Typescript I'm wanting to work with. Theres 3 roles,
enum Type {
FRUIT = 0x1,
VEGGIE = 0x2,
BOTH = FRUIT | VEGGIE
}
class Thing {
role:number;
constructor(role:Type){
this.role = role;
}
getRole(){
return this.role;
}
is(role:Type) {
return !!(this.role & role);
}
}
var whatever = new Thing(Type.FRUIT);
console.log('fruit', whatever.is(Type.FRUIT));
console.log('veggie', whatever.is(Type.VEGGIE));
console.log('both', whatever.is(Type.BOTH));
// fruit true
// veggie false
// both true
I conceptually see why "both" is coming back as "true", but my bit math isn't great.
When the role is either FRUIT
or VEGGIE
, the others are false. When it's set to BOTH
, all should be true.
Tried a few combinations of shifts and bit operations, but I can't get that output. If I try them separate it's fine, but I'd like to use combinations of bits to build.
Upvotes: 1
Views: 6777
Reputation: 251262
When you perform a bitwise &
operation the result is that the bits turned on in both values used in the expression.
For example (taken from Pro TypeScript, p 207)
a 1011
&
b 1101
= 1001
The first column, both values are "switched on (1)", so the result is also switched on. The second column, a
is switched off, so the result is 0
, the third column b
is off, so again a 0
and finally the last column both are on, so a 1
.
In your case, it is even simpler because you are dealing with such small numbers...
a 01 // FRUIT
&
b 11 // ALL
= 01 // FRUIT
So the result is 01
, or 1
if you have ten fingers.
If you use a double-bang !!
to convert 1
to to a boolean (I call this slacker parsing), you'll get true
because 1
is truth-y. This doesn't answer the question you were really asking, which is "does this bit flag match".
This is why this.role & role === role
is the correct code, because you won't get a mistake from the "truthiness" of the value 1
.
Upvotes: 7
Reputation: 21518
return !!(this.role & role);
Your version works as isAny
, but you want it to work as isAll
:
return (this.role & role) === role;
Upvotes: 6