I have a couple of classes BitMask & BitMaskLarge that both implement an interface IBitMask that exposes functionality to perform bitwise logic operations, etc. The BitMask class contains the a private _mask field of type long and the BitMaskLarge class contains a private _masks array of longs.
The end user works with IBitMask and the implementation details of each of the classes should be transparent to them, such as how the bitwise logic is implemented when both inputs are of one type as opposed to of one type each.
When creating an IBitMask a BitMaskFactory is used that returns the appropriate type, based on the bitwidth passed into the constructor.
The problem occurs when setting a bit in the bit mask using the SetBitIndex method. If the bit is outside the bounds of the current mask, BitMaskLarge simply adds another element to _masks and sets the appropriate bit. However BitMask cannot go beyond 64 bits and so need to convert to a BitMaskLarge. Obviously this is impossible when calling bitmask.SetBitIndex(100) on the BitMask class, which should set the bit at index 100.
One possible solution I can think of would be to make SetBitIndex internal, and to create a static method on the BitMaskFactory that returned the new or updated IBitMask. This is not ideal as it is not natural to use. If anyone has a better solution to this problem, I’d like to hear it. All ideas are welcome, no matter how fundamental the changes required.
You can make types implementing
IBitMaskimmutable, and have mutating operations return a new instance. This would run like this:Making the instances immutable also offers thread safety “for free”.
If you find this inconvenient, you can solve it by adding another layer of abstraction:
This loses you the thread safety though.
Update:
You shouldn’t really go to all this trouble unless a
BitMaskLargeis much more expensive for you than aBitMask, and you also expect nearly all masks to be simpleBitMasks.