banner



How To Check If A Bit Is 0

Working on bytes, or data types comprising of bytes like ints, floats, doubles or even data structures which stores large corporeality of bytes is normal for a developer. In some cases, a programmer needs to go beyond this - that is to say that in a deeper level where the importance of $.25 is realized.

Operations with bits are used in Data compression (data is compressed by converting it from one representation to another, to reduce the space) ,Sectional-Or Encryption (an algorithm to encrypt the data for safety issues). In club to encode, decode or compress files nosotros have to excerpt the information at bit level. Bitwise Operations are faster and closer to the organisation and sometimes optimize the programme to a good level.

Nosotros all know that 1 byte comprises of 8 bits and any integer or character tin exist represented using $.25 in computers, which we call its binary form(contains but 1 or 0) or in its base 2 form.
Example:
ane) 14 = {1110 }2
= 1 * 2three + 1 * 2two + 1 * twoane + 0 * 20
= fourteen.

2) 20 = {10100 }2
= 1 * 2four + 0 * 23 + ane * 2ii + 0 * 21 + 0 * ii0
= 20.

For characters, nosotros utilize ASCII representation, which are in the form of integers which again tin can exist represented using bits as explained above.

Bitwise Operators:

At that place are different bitwise operations used in the bit manipulation. These scrap operations operate on the individual bits of the chip patterns. Bit operations are fast and can be used in optimizing time complexity. Some common fleck operators are:

Non ( ~ ): Bitwise NOT is an unary operator that flips the bits of the number i.e., if the ith fleck is 0, information technology will change information technology to 1 and vice versa. Bitwise Non is nothing but simply the 1's complement of a number. Lets accept an case.
N = 5 = (101)2
~N = ~v = ~(101)2 = (010)2 = 2

AND ( & ): Bitwise AND is a binary operator that operates on 2 equal-length bit patterns. If both bits in the compared position of the fleck patterns are 1, the bit in the resulting chip pattern is 1, otherwise 0.
A = 5 = (101)2 , B = 3 = (011)2 A & B = (101)2 & (011)2= (001)two = 1

OR ( | ): Bitwise OR is also a binary operator that operates on two equal-length fleck patterns, like to bitwise AND. If both bits in the compared position of the bit patterns are 0, the bit in the resulting bit pattern is 0, otherwise 1.
A = 5 = (101)ii , B = 3 = (011)2
A | B = (101)two | (011)2 = (111)2 = 7

XOR ( ^ ): Bitwise XOR also takes two equal-length bit patterns. If both bits in the compared position of the scrap patterns are 0 or ane, the bit in the resulting fleck design is 0, otherwise 1.
A = 5 = (101)ii , B = iii = (011)2
A ^ B = (101)2 ^ (011)2 = (110)2 = half-dozen

Left Shift ( << ): Left shift operator is a binary operator which shift the some number of bits, in the given bit pattern, to the left and append 0 at the terminate. Left shift is equivalent to multiplying the bit pattern with 2k ( if we are shifting one thousand bits ).
i << 1 = 2 = 21
one << ii = 4 = twoii i << 3 = viii = 2iii
1 << four = 16 = two4

i << n = iidue north

Correct Shift ( >> ): Right shift operator is a binary operator which shift the some number of bits, in the given bit pattern, to the right and append 1 at the end. Right shift is equivalent to dividing the bit pattern with 2k ( if nosotros are shifting g bits ).
4 >> 1 = 2
6 >> i = 3
5 >> 1 = two
sixteen >> 4 = i

enter image description here

Bitwise operators are good for saving space and sometimes to cleverly remove dependencies.

Notation: All left and right side taken in this commodity, are taken with reference to the reader.

Lets hash out some algorithms based on bitwise operations:

1) How to check if a given number is a power of 2 ?
Consider a number Due north and you demand to find if Due north is a power of 2. Unproblematic solution to this problem is to repeated divide N by 2 if N is even. If we end up with a i and then N is power of ii, otherwise non. There are a special case also. If North = 0 then it is not a power of 2. Allow'south code it.

Implementation:

          bool isPowerOfTwo(int x) {     if(x == 0)         return faux;     else     {         while(x % 2 == 0) x /= 2;         return (x == 1);         } }                  

Above function will return true if x is a power of 2, otherwise false.
Fourth dimension complexity of the above lawmaking is O(logN).

The aforementioned problem can exist solved using fleck manipulation. Consider a number 10 that we need to check for being a power for 2. At present think well-nigh the binary representation of (x-one). (ten-1) will have all the bits aforementioned as x, except for the rightmost 1 in x and all the bits to the right of the rightmost 1.
Let, x = iv = (100)2
x - one = 3 = (011)2
Allow, x = 6 = (110)2
x - one = 5 = (101)2

It might not seem obvious with these examples, but binary representation of (10-1) can be obtained by simply flipping all the bits to the right of rightmost 1 in 10 and also including the rightmost 1.

Now think about 10 & (x-1). 10 & (x-1) volition have all the bits equal to the x except for the rightmost 1 in x.
Let, x = 4 = (100)2
x - one = three = (011)2
10 & (x-1) = iv & 3 = (100)2 & (011)ii = (000)2
Let, x = vi = (110)2
x - 1 = 5 = (101)ii
x & (x-1) = 6 & five = (110)ii & (101)2 = (100)ii

Properties for numbers which are powers of 2, is that they have 1 and only one bit set in their binary representation. If the number is neither goose egg nor a power of two, it will have 1 in more one identify. So if x is a power of ii then x & (ten-ane) will be 0.

Implementation:

          bool isPowerOfTwo(int 10) {     // ten will check if x == 0 and !(x & (x - 1)) will check if 10 is a power of 2 or not     render (x && !(10 & (x - 1))); }                  

2) Count the number of ones in the binary representation of the given number.

The basic approach to evaluate the binary form of a number is to traverse on it and count the number of ones. But this approach takes log2N of fourth dimension in every instance.

Why log2N ?
As to get a number in its binary form, nosotros have to divide it by 2, until it gets 0, which will accept logtwoNorthward of fourth dimension.

With bitwise operations, nosotros tin can use an algorithm whose running time depends on the number of ones nowadays in the binary course of the given number. This algorithm is much better, equally it will reach to logN, but in its worst case.

          int count_one (int due north)     {         while( n )         {         n = n&(n-1);            count++;         }         return count; }                  

Why this algorithm works ?
As explained in the previous algorithm, the human relationship betwixt the bits of x and 10-1. Then as in x-i, the rightmost 1 and bits right to it are flipped, then past performing ten&(x-1), and storing it in ten, volition reduce x to a number containing number of ones(in its binary form) less than the previous state of x, thus increasing the value of count in each iteration.

Example:
northward = 23 = {10111}two .
1. Initially, count = 0.
ii. Now, n will change to n&(n-i). Every bit n-1 = 22 = {10110}two , and then n&(n-1) volition be {101112 & {10110}2, which will be {10110}2 which is equal to 22. Therefore n will change to 22 and count to 1.
3. As n-ane = 21 = {10101}2 , then n&(n-ane) will be {10110}2 & {10101}2, which volition be {10100}two which is equal to 20. Therefore northward will modify to xx and count to 2.
4. Equally n-one = 19 = {10011}2 , and so n&(northward-i) will be {10100}2 & {10011}2, which will be {10000}2 which is equal to 16. Therefore north will change to xvi and count to three.
5. Every bit n-1 = 15 = {01111}2 , then n&(n-1) will be {10000}ii & {01111}ii, which will be {00000}2 which is equal to 0. Therefore n volition alter to 0 and count to four.
half dozen. As due north = 0, the the loop will finish and gives the result as 4.

Complexity: O(M), where Thousand is the number of ones present in the binary form of the given number.

iii) Cheque if the ith fleck is fix in the binary form of the given number.

To check if the ith flake is set or not (1 or non), we tin can use AND operator. How?

Let's say nosotros have a number N, and to check whether it's ith bit is set up or non, we tin can AND it with the number twoi . The binary form of iii contains but ith chip as set up (or ane), else as is 0 at that place. When nosotros will AND it with N, and if the ith fleck of N is fix, then information technology will return a non nothing number (2i to be specific), else 0 will be returned.

Using Left shift operator, we tin write twoi equally 1 << i . Therefore:

          bool check (int N) {     if( North & (1 << i) )         return true;     else         return fake; }                  

Example:
Let'due south say N = 20 = {10100}ii. Now let's check if it's second flake is set or not(starting from 0). For that, we have to AND it with two2 = 1<<2 = {100}2 .
{10100} & {100} = {100} = 22 = 4(non-nil number), which means information technology'south 2nd bit is ready.

4) How to generate all the possible subsets of a gear up ?

A big reward of bit manipulation is that it can help to iterate over all the subsets of an North-element ready. As we all know there are 2N possible subsets of whatsoever given set with N elements. What if we represent each element in a subset with a flake. A chip tin can be either 0 or 1, thus we can use this to denote whether the corresponding element belongs to this given subset or not. So each bit pattern will represent a subset.

Consider a gear up A of 3 elements.
A = {a, b, c}

Now, we demand 3 $.25, one scrap for each chemical element. 1 stand for that the respective chemical element is present in the subset, whereas 0 represent the respective element is not in the subset. Let'southward write all the possible combination of these 3 bits.

0 = (000)2 = {}
1 = (001)two = {c}
ii = (010)2 = {b}
iii = (011)2 = {b, c}
four = (100)ii = {a}
5 = (101)2 = {a, c}
6 = (110)ii = {a, b}
7 = (111)2 = {a, b, c}

Pseudo Code:

          possibleSubsets(A, N):     for i = 0 to two^N:         for j = 0 to N:             if jth bit is set in i:                 print A[j]         print '\n'                  

Implementation:

          void possibleSubsets(char A[], int N) {     for(int i = 0;i < (ane << N); ++i)     {         for(int j = 0;j < Northward;++j)             if(i & (one << j))                 cout << A[j] << ' ';         cout << endl; } }                  

5) Discover the largest power of 2 (most meaning flake in binary form), which is less than or equal to the given number N.

Thought: Change all the bits which are at the right side of the virtually significant digit, to 1.

Property: As we know that when all the $.25 of a number N are 1, so N must exist equal to the 2i -1 , where i is the number of $.25 in Northward.

Example:
Allow'south say binary form of a N is {1111}two which is equal to 15.
xv = 2four-i, where 4 is the number of $.25 in N.

This holding tin can be used to find the largest power of 2 less than or equal to N. How?
If we somehow, change all the bits which are at right side of the about significant bit of North to 1, and then the number volition get x + (ten-1) = 2 * x -1 , where x is the required respond.
Example:
Let's say North = 21 = {10101}, here almost meaning chip is the fourth one. (counting from 0th digit) and and so the answer should be 16.
Then lets change all the correct side bits of the most significant bit to 1. Now the number changes to
{11111} = 31 = 2 * 16 -1 = Y (allow'southward say).
At present the required answer is (Y+1)>>1 or (Y+1)/2.

Now the question arises here is how tin we change all right side bits of most significant flake to ane?

Permit's have the N as 16 bit integer and binary grade of Due north is {1000000000000000}.
Here nosotros have to change all the right side $.25 to ane.

Initially we will copy that most meaning chip to its next right side by:

Due north = Due north | (North>>1).

enter image description here

Equally you can see, in above diagram, after performing the performance, rightmost chip has been copied to its adjacent place.

Now we will copy the 2 rightmost set bits to their adjacent right side.
N = N | (N>>two).
enter image description here

At present we will re-create the four rightmost ready fleck to their next correct side.

N = N | (N>>iv)
enter image description here

Now we volition re-create these eight rightmost fix bits to their adjacent right side.

N = Due north| (Northward>>8)
enter image description here

At present all the correct side bits of the most significant set bit has been changed to ane .This is how we tin change right side bits. This explanation is for xvi bit integer, and it can exist extended for 32 or 64 bit integer too.

Implementation:

          long largest_power(long N) {     //changing all right side bits to one.     N = N| (N>>one);     North = Northward| (Due north>>2);     N = N| (N>>4);     N = N| (Due north>>8);   //as now the number is 2 * ten-1, where ten is required respond, then calculation i and dividing it by  two.              render (Due north+1)>>ane;  }                  

Tricks with Bits:

1) x ^ ( 10 & (x-1)) : Returns the rightmost ane in binary representation of ten.

As explained above, (x & (x - 1)) will have all the $.25 equal to the ten except for the rightmost 1 in ten. So if we practise bitwise XOR of x and (x & (x-1)), it will but return the rightmost 1. Let's come across an example.
x = 10 = (1010)two
x & (ten-ane) = (1010)ii & (1001)two = (1000)2
x ^ (x & (x-1)) = (1010)2 ^ (1000)ii = (0010)2

two) x & (-x) : Returns the rightmost ane in binary representation of x

(-x) is the two'southward complement of 10. (-x) will be equal to one's complement of x plus 1.
Therefore (-x) will take all the $.25 flipped that are on the left of the rightmost 1 in x. So x & (-ten) will return rightmost 1.

x = x = (1010)2
(-x) = -x = (0110)two
x & (-x) = (1010)2 & (0110)2 = (0010)2

3) x | (1 << n) : Returns the number x with the nth bit fix.

(1 << due north) will return a number with only nth bit fix. So if nosotros OR it with x information technology will ready the nth fleck of 10.
x = 10 = (1010)2 n = ii
1 << northward = (0100)2
x | (1 << n) = (1010)two | (0100)2 = (1110)two

Applications of bit operations:

1) They are widely used in areas of graphics ,specially XOR(Exclusive OR) operations.
two) They are widely used in the embedded systems, in situations, where we need to set/clear/toggle only one single bit of a specific register without modifying the other contents. We can do OR/AND/XOR operations with the advisable mask for the flake position.
three) Data construction like n-fleck map can be used to allocate n-size resource pool to represent the current status.
4) Bits are used in networking, framing the packets of numerous bits which is sent to another system by and large through any type of series interface.

To see a artistic use of Bitwise operators, you tin refer this amazing article , where the fleck wise operations are smartly used while developing an online calendar for events.

                            

Source: https://www.hackerearth.com/practice/notes/bit-manipulation/

0 Response to "How To Check If A Bit Is 0"

Post a Comment

Iklan Atas Artikel

Iklan Tengah Artikel 1

Iklan Tengah Artikel 2

Iklan Bawah Artikel