Some questions and understandings about bit operation

Some questions and understandings about bit operation

1. What is the first bit operation?

2. What can bit operations do?

3. Why use bit operations instead of other operations?

4. Since the operation in place is used, how to use its operators and what is the application scenario?

For the above personal questions, I surf and read books to collect some information and make the following arrangement.

What is the first bit operation?

In the bit operation that I actually write code, the bit operator is a calculation symbol. More directly, it is a special operator for binary calculation. For example, if 1111 (15) is shifted to the right by one (two) bits, it becomes 0111 (7) (00113); If it is moved to the left by one (two) bits, it becomes 11110 (30) (111100 60). From the above calculation, we can actually draw a small conclusion first: if the binary number is moved to the right by several bits, it is to divide the original number by several powers of 2; If the binary number is moved to the left by a few bits, it is to multiply the original number by several powers of 2 (some people may wonder that moving 1111 to the right by two bits is 3.5, how can it be 3? Because the value of int is rounded to 0).

Wikipedia explains that bit operations are unary and binary operations on arrays or binary numbers.

That is, bit operation is an operation based on the binary representation of an integer.

What can bit operations do?

Bit operation is a kind of mathematical symbol for binary operation. More fundamentally, it is an operation with higher efficiency than addition, subtraction, multiplication and division. There are several operators for bit operations (& and, | or, ^ XOR, ~ negate, > > shift right, < < shift left)

Why use bit operations instead of other operations?

Wikipedia says: on many ancient microprocessors, bit operations are slightly faster than addition and subtraction operations, and usually bit operations are much faster than multiplication and division operations. In the modern architecture, the operation speed of the bit operation is usually the same as that of the addition operation (still faster than the multiplication operation), but the power consumption is usually small because the resource usage is reduced. (I hope you can give me some advice on how to do this experiment.)

Since the bit operation is used, how to use its operators and what is the application scenario?

&And operator

The rule is: when both digits are 1, it is 1

/**
 * & The operation rule is: when both digits are 1, it is 1
 * 0b Represents binary
 * 101 --> 5
 * 100 --> 4
 * After the & operation, it becomes 100 -- > 4
 */
int aa = 0b101;
int bb = 0b100;
System.out.println(aa & bb); // 4
//The same is true of octal
//101 & 100 --> 100 64
int cc = 0101;
int dd = 0100;
System.out.println(cc & dd);//64
//Hexadecimal
//101 & 100 --> 100 256
int ee = 0x101;
int ff = 0x100;
System.out.println(ee & ff);//256

Purpose:

1. Reset

If you want to clear a cell to zero, even if all its binary bits are 0, as long as it is added to a value whose bits are all zero, the result is zero.

2. Take a number of finger positions

For example, to retrieve the lower 4 bits of X=1010 1110, it is only necessary to find another number y, so that the lower 4 bits of Y are 1 and the remaining bits are 0, that is, Y=0000 1111. Then, X and y are bitwise and (X & y = 0000 1110) to obtain the specified position of X.

int ii = 0b10101110;
int jj = 0b00001111;
String s = Integer.toBinaryString(ii & jj);
System.out.println(s); // 1110

3. Judge parity

As long as the last bit is 0 or 1, 0 is an even number and 1 is an odd number. Therefore, if ((A & 1) = = 0) can be used instead of if (a% 2 = = 0) to judge whether a is an even number.

 public static void test(int i) { // 0011  3
        if ((i & 1) == 0) { //1:0001
            System.out.println(i + "Is an even number");
        } else {
            System.out.println(i + "Is an odd number");
        }
    }

|Or operator

The rule is: two digits, 1 means 1, otherwise 0

 /**
  * | The operation rule is: two digits, 1 means 1, otherwise 0
  * 0b Represents binary
  * 101 --> 5
  * 100 --> 4
  * After | operation, it becomes 101 -- > 5
  */
int aa = 0b101;
int bb = 0b100;
System.out.println(aa | bb);
//The same is true of octal
//101 | 100 --> 101 65
int cc = 0101;
int dd = 0100;
System.out.println(cc | dd);//65
//Hexadecimal
//101 | 100 --> 101 257
int ee = 0x101;
int ff = 0x100;
System.out.println(ee | ff);//257

Purpose:

1. It is often used to set some bits of a data to 1

For example, if the lower 4 bits of the number X=1010 1110 are set to 1, it is only necessary to find another number y, so that the lower 4 bits of Y are 1 and the remaining bits are 0, that is, Y=0000 1111, and then perform bitwise OR operation (X|Y=1010 1111) on X and y.

int ii = 0b10101110;
int jj = 0b00001111;
String s = Integer.toBinaryString(ii | jj);
System.out.println(s);//10101111

^Exclusive or operator

Operation rule: two digits, the difference is 1, and the same is 0 (I remember this: the same is gone (i.e. 0), and the difference is left (i.e. 1)

/**
 * ^ The operation rule is: two digits, the difference is 1, and the same is 0
 * 0b Represents binary
 * 111 --> 7
 * 100 --> 4
 * After ^ operation, it becomes 011 -- > 3
 */
int aa = 0b111;
int bb = 0b100;
System.out.println(aa ^ bb);//3
//The same is true of octal
//111 ^ 100 --> 011 9
int cc = 0111;
int dd = 0100;
System.out.println(cc ^ dd);//9
//Hexadecimal
//111 ^ 100 --> 011 257
int ee = 0x111;
int ff = 0x100;
System.out.println(ee ^ ff);//17

Purpose:

1. Flip finger positioning

For example, if the lower 4 bits of the number X=1010 1110 are inverted, it is only necessary to find another number y, so that the lower 4 bits of Y are 1 and the remaining bits are 0, that is, Y=0000 1111. Then, X and y are XORed (X^Y=1010 0001) to obtain

int ii = 0b10101110;
int jj = 0b00001111;
String s = Integer.toBinaryString(ii ^ jj);
System.out.println(s); //The output is 1010 0001

2. Exchange two numbers

public static void Swap(int a,int b){ //Incoming 1 2
        System.out.println("Before exchange:");
        System.out.println(a+"\t"+b);
        if(a!=b){   //a = 1  b = 2
            a^=b;  // a:0001  b:0010
            b^=a;  // a:0011  b:0010  ----> 0001  b=1
            a^=b;  // a:0011  b:0001  ----> 0010  a=2
        }
        System.out.println("After exchange:");
        System.out.println(a+"\t"+b);
}

/*The output result is: 
Before exchange:
1 2
 After exchange:
2 1
*/

< < left shift operator > > right shift operator

Operation rule: if the binary number moves to the right by several bits, it is to divide the original number by several powers of 2; If the binary number is moved to the left by a few bits, it is to multiply the original number by several powers of 2

//Take binary as an example
int bb = 0b100; //4
System.out.println(bb >> 1);//2
System.out.println(bb << 1);//8
System.out.println(bb >> 2);//1
System.out.println(bb << 2);//16

~Negation operator (different from logical not)

Operation rule: the binary number is inverted by bit, 1 is inverted to 0, 0 is inverted to 1, and the result is equal to the complement of the value minus one.

int gg = 0b10101011 //Decimal 171
/* 
After the binary is negated, 0b010100 is equivalent to 171 (complement-1) 
171 The complement of is 
First, reverse 10101011 to 01010100 (inverse code), and inverse code + 1 = complement
01010101 171 complement
*/

If complement arithmetic is used, ~ x = -x − 1.

int gg = 0b1100; //12
System.out.println(~gg); // -13

Note: ~ operator has higher priority than arithmetic operator, logical operator and relational operator.

Tags: Java

Posted by kailien on Tue, 16 Aug 2022 10:00:17 +0300