views:

210

answers:

4

I need a little help with bitmap operations in C#

I want to take a UInt16, isolate an arbitrary number of bits, and set them using another UInt16 value.

Example:

10101010  -- Original Value
00001100  -- Mask - Isolates bits 2 and 3

Input        Output
00000000  -- 10100010
00000100  -- 10100110
00001000  -- 10101010
00001100  -- 10101110
                 ^^
+4  A: 

It seems like you want:

(orig & ~mask) | (input & mask)

The first half zeroes the bits of orig which are in mask. Then you do a bitwise OR against the bits from input that are in mask.

JSBangs
+2  A: 
newValue = (originalValue & ~mask) | (inputValue & mask);

originalValue -> 10101010
inputValue    -> 00001000  
mask          -> 00001100 
~mask         -> 11110011

(originalValue & ~mask)
  10101010
& 11110011
----------
  10100010
      ^^
      Cleared isolated bits from the original value

(inputValue & mask)
  00001000  
& 00001100 
----------
  00001000


newValue =      
  10100010
| 00001000
----------
  10101010
Chris Taylor
This doesn't give the input/output values that the OP shows.
JSBangs
I think the "Input" in the examples is meant to be the mask, so the RH of the `|` can be reduced to mask.
Mark H
@Mark: The input in the examples is the new values for each of the bits in the mask.
Robert Harvey
The updated answer is correct, so I dropped my -1
JSBangs
A: 

Something like this?

static ushort Transform(ushort value){
    return (ushort)(value & 0x0C/*00001100*/ | 0xA2/*10100010*/);
}

This will convert all your sample inputs to your sample outputs. To be more general, you'd want something like this:

static ushort Transform(ushort input, ushort mask, ushort bitsToSet){
    return (ushort)(input & mask | bitsToSet & ~mask);
}

And you would call this with:

Transform(input, 0x0C, 0xA2);

For the equivalent behavior of the first function.

P Daddy
A: 

A number of the terser solutions here look plausible, especially JS Bangs', but don't forget that you also have a handy BitArray collection to use in the System.Collections namespace: http://msdn.microsoft.com/en-us/library/system.collections.bitarray.aspx

Paul Sasik
I considered this, but it doesn't appear to have a masking capability. You have to set or get each bit individually.
Robert Harvey