Recipe 1.4 Using the Bitwise Complement Operator with Various Data Types
Problem
The
bitwise complement operator (~) is overloaded to
work directly with int, uint,
long, ulong, and enumeration
data types consisting of the underlying types int,
uint, long, and
ulong. However, you need to perform a different
bitwise complement operation on a data type.
Solution
You must cast the resultant value of the bitwise operation to the
type you wish to work. The following code demonstrates this technique
with the byte data type:
byte y = 1;
byte result = (byte)~y;
The value assigned to result is
254.
Discussion
The following code shows incorrect use of the bitwise complement
operator on the byte data type:
byte y = 1;
Console.WriteLine("~y = " + ~y);
This code outputs the following surprising value:
-2
Clearly, the result from performing the bitwise complement of the
byte variable is incorrect; it should be
254. In fact, byte is an
unsigned data type, so it cannot be equal to a negative number. If we
rewrite the code as follows:
byte y = 1;
byte result = ~y;
we get a compile-time error: "Cannot implicitly
convert type `int' to `byte.'" This
error message gives some insight into why this operation does not
work as expected. To fix this problem, we must explicitly cast this
value to a byte before we assign it to the
result variable, as shown here:
byte y = 1;
byte result = (byte)~y;
This cast is required because the bitwise operators are only
overloaded to operate on six specific data types:
int, uint,
long, ulong,
bool, and enumeration data types. When one of the
bitwise operators is used on another data type, that data type is
converted to the next closest data type of the six supported data
types. Therefore, a byte data type is converted to
an int before the bitwise complement operator is
evaluated:
0x01 // byte y = 1;
0xFFFFFFFE // The value 01h is converted to an int and its
// bitwise complement is taken
0xFE // The resultant int value is cast to its original byte data type
Notice that the int data type is a signed data
type, unlike the byte data type. This is why we
receive -2 for a result instead of the expected
value 254. This conversion of the
byte data type to its nearest equivalent is called
numeric
promotion. Numeric promotion also comes into play when you
use differing data types with binary operators, including the bitwise
binary operators.
 |
Numeric promotion is discussed in detail in the
C# Language Specification document in
section 7.2.6 (this document is found in the directory \MicrosoftVisual Studio .NET 2003\Vc7\1033
below the .NET 2003 installation directory). Understanding how
numeric promotion works is essential when using operators on
differing data types and when using operators with a data type that
it is not overloaded to handle. Knowing this can save you hours of
debugging time.
|
|
|