Friday, November 4, 2011

Left Shift Operator in C programming

Left Shift Operator

This is similar to the right shift operator, the only difference being that the bits are shifted to the left, and for each bit shifted, a 0 is added to the right of the number. The following program should clarify my point.
main( )
{
int i = 5225, j, k ;
printf ( "\nDecimal %d is same as ", i ) ;
showbits ( i ) ;
for ( j = 0 ; j <= 4 ; j++ )
{
k = i <<j ;
printf ( "\n%d left shift %d gives ", i, j ) ;
showbits ( k ) ;
}
}

The output of the above program would be...
Decimal 5225 is same as binary 0001010001101001
5225 left shift 0 gives 0001010001101001
5225 left shift 1 gives 0010100011010010
5225 left shift 2 gives 0101000110100100
5225 left shift 3 gives 1010001101001000
5225 left shift 4 gives 0100011010010000
Having acquainted ourselves with the left shift and right shift operators, let us now find out the practical utility of these operators.
In DOS/Windows the date on which a file is created (or modified) is stored as a 2-byte entry in the 32 byte directory entry of that file. Similarly, a 2-byte entry is made of the time of creation or modification of the file. Remember that DOS/Windows doesn’t store the date (day, month, and year) of file creation as a 8 byte string, but as a codified 2 byte entry, thereby saving 6 bytes for each file entry in the directory. The bitwise distribution of year, month and date in the 2-byte entry is shown in Figure 14.3.





On similar lines, left shifting by 7, followed by right shifting by 12 yields month





Finally, for obtaining the day, left shift date by 11 and then right shift the result by 11. Left shifting by 11 gives 0100100000000000. Right shifting by 11 gives 0000000000001001.
This entire logic can be put into a program as shown below:
/* Decoding date field in directory entry using bitwise operators */
main( )
{
unsigned int d = 9, m = 3, y = 1990, year, month, day, date ;
date = ( y - 1980 ) * 512 + m * 32 + d ;
printf ( "\nDate = %u", date ) ;






DOS/Windows converts the actual date into a 2-byte value using the following formula:
date = 512 * ( year - 1980 ) + 32 * month + day
Suppose 09/03/1990 is the date, then on conversion the date will be,
date will be,
date = 512 * ( 1990 - 1980 ) + 32 * 3 + 9 = 5225
The binary equivalent of 5225 is 0001 0100 0110 1001. This binary value is placed in the date field in the directory entry of the file as shown below




Just to verify this bit distribution, let us take the bits representing the month,
month = 0011
= 1 * 2 + 1 * 1
= 3
Similarly, the year and the day can also be verified.
When we issue the command DIR or use Windows Explorer to list the files, the file’s date is again presented on the screen in the usual date format of mm/dd/yy. How does this integer to date conversion take place? Obviously, using left shift and right shift operators.
When we take a look at Figure 14.4 depicting the bit pattern of the 2- byte date field, we see that the year, month and day exist as a bunch of bits in contiguous locations. Separating each of them is a matter of applying the bitwise operators.
For example, to get year as a separate entity from the two bytes entry we right shift the entry by 9 to get the year. Just see, how...
year = 1980 + ( date >> 9 ) ;
month = ( (date << 7 ) >> 12 ) ;
day = ( (date << 11 ) >> 11 ) ;
printf ( "\nYear = %u ", year ) ;
printf ( "Month = %u ", month ) ;
printf ( "Day = %u", day ) ;
}
And here is the output...
Date = 5225
Year = 1990 Month = 3 Day = 9

1 comment: