Beginner's manual that uses enumeration variables as the marker
When I was hanging out in the Visual C ++ Forum (again), I had to face the fact that many beginners lack common sense about bitwise operations, usually binary. After I knocked on my fingers and wrote a long answer to the ignorant, it was obvious that I had to share this confusing knowledge with the community through this article.
If you want to have a deeper understanding of the C/C ++ bit operation knowledge, you can read the comprehensive article "bit operation Introduction" written by pjarends. You can also perform complex but effective bit hacking. Read this article: Bit twiddling hacks written by Sean wing Anderson.
I do my best to present everything that I can do with bit operations, tag operations, and all other binary-related things.
Fact
We found that one of the most common bit operations is when a Library provides an enumeration variable set and the function uses DWORD as the standard BIT container. Let's take an Enum as an example and define it as follows:
Enum {
Style1 = 1,
Style2 = 2,
Style3 = 4,
Style4 = 8,
Style5 = 16,
Style6 = 32,
Style7 = 64,
Style8 = 128
};
As we can see, these constants are the N power of 2. To understand why these constants are selected, we must study the binary representation.
1-> 0 B 00000000 00000000 00000000 00000001
2-> 0 B 00000000 00000000 00000000 00000010
4-> 0 B 00000000 00000000 00000000 00000100
8-> 0 B 00000000 00000000 00000000 00001000
16-> 0 B 00000000 00000000 00000000 00010000
32-> 0 B 00000000 00000000 00000000 00100000
64-> 0 B 00000000 00000000 00000000 01000000
128-> 0b 00000000 00000000 00000000
Note that only one of these values is set at a time, and all other bits are equal to 0. Now you can see that one of the major advantages of this is that each bit is represented as a functional standard BIT (here each bit represents a type ). To avoid using Boolean variables as many as the scalar bits, we can now imagine a method that can mix these scalar bits into a variable. Consider the following example:
0b 00000000 00000000 00000000 00100101
Type 1, 3, and 6
Operation
Now we are faced with a problem. C ++ does not directly process binary data. We have to use bitwise operations instead. We know there are three atomic bitwise operators in ascending order of priority: Or (|), and (&) Not (~). Their behavior is as follows:
X y | x Y & X ~
----------------------
0 0 0 0 0 0 1
0 1 1 0 1 0 1 0
1 0 1 1 0 0
1 1 1 1 1
Knowing this, we can use these operations to construct the above-mentioned hybrid scalar bits. In the statement example of style1 | style3 | style6, we use constants such as "or.
0b 00000000 00000000 00000000 00000001 <-style1
0b 00000000 00000000 00000000 00000100 <-style3
0b 00000000 00000000 00000000 00100000 <-style6
-----------------------------------------------
0b 00000000 00000000 00000000 00100101 <-style1 | style3 | style6
We can see that the bitwise operation "or" is very like the "plus" (+) operation. But if you want to use + instead of |, you should be very careful. The reason is very simple. The result of "add" 1 + 1 is 0 (there is a carry ). If all constants are strictly different, there will be no problem, but it is a bad habit to use other operations instead of bitwise operations to process binary data. I will not discuss it in detail.
DWORD operations by bit
The DWORD type is generally used for such a hybrid tag. However, this is not a mandatory clause. We can also use any integer (char, short, Int, long...) to implement this. A dword is an unsigned 32-bit integer (like the binary representation in this article ). Let's imagine that when we have a DWORD in the function, we will pass another one in the parameter. How can I know which one is set to 1 when I call a function? This is simple. Let's look at it!
For example, we want to know whether the sytle8 bit is set to 1 in the DWORD passed in the parameter. We must have a mask that we can purchase and obtain the logical sum of parameters. In practice, the mask is the same as the constant we test, so no amount is required.
To create a mask:
DWORD parameter-> 0b 00000000 00000000 00000000 00100101
Style8 mask-> 0b 00000000 00000000 00000000 10000000
----------------------------------------
Bitwise AND-> 0b 00000000 00000000 00000000 00000000 <-0x00000000
DWORD parameter-> 0b 00000000 00000000 00000000 10100101
Style8 mask-> 0b 00000000 00000000 00000000 10000000
----------------------------------------
Bitwise AND-> 0b 00000000 00000000 00000000 10000000 <-style8
If the "and" Operation returns 0, this bit is set to 1. Otherwise, the system returns the mask itself.
Okay. Now, in practice, we can see that
Void setstyles (DWORD dwstyles ){
If (style1 & dwstyles) = style1 ){
// Apply style 1
}
Else if (style2 & dwstyles) = style2 ){
// Apply style 2
}
Else if (style3 & dwstyles) = style3 ){
// Apply Style 3
}
// Etc...
}
I have not mentioned "no" (~) for the third-digit operation "(~). It is usually used when you already have a single bit set. Some bits are set to 1 while others are not, and you will not clear any of them, the following sample code shows how to implement these functions.
Void removestyle5 (DWORD & dwstyles ){
If (style5 & dwstyles) = style5 ){
Dwstyles & = ~ Style5;
}
}
I have not mentioned another bitwise operation "XOR" (^). The only reason I mentioned it at last is that it is not an atomic bitwise operation, that is to say, we cannot reconstruct its behavior with the bitwise operators mentioned above.
# Define XOR (A, B) ()&~ (B) | (B )&~ ()))
In any case, this operation is easy to switch a single bit.
Void switchstyle5 (DWORD & dwstyles ){
Dwstyles ^ = style5;
}
Link
The following link provides some additional bit operation knowledge. If you want to learn more about bit operations
An Introduction to bitwise operators by PJ arends.
Bit twiddling hacks by Sean wing Anderson.
Conclusion
Okay. If you read this, I hope I can help you. If you find the error here, don't hesitate to point it out, so I can correct it quickly.
Original article: http://www.codeproject.com/useritems/Binary_Guide.asp
The translation in this article is not very accurate, but the basic meaning is expressed. I hope you can correct the wrong forwhoever@gmail.com.