cbit-manipulationscanfbitwise-operators

Finding the bigger number using bitwise operation in C


I am trying to write a computer programme that will take two numbers from the user as inputs and will print the bigger number using bitwise operation. I want it to end the programme and return 1 if user inputs negative number or floating number or keep looping back otherwise.

So I wrote the following -

#include <stdio.h>

unsigned int big (unsigned int x, unsigned int y)
{
    unsigned int big = x, small = y;
    for (;;)
    {
        big >>= 1; small >>= 1;
        if ((big == 0) || (small == 0))
        {
            if (big == 0) { return y; }
            if (small == 0) { return x; }
        }
    }
}

int main (void)
{
    for (;;)
    {
        unsigned int x, y;
        printf("Give me a number : ");
        if ((scanf("%u", &x) != 1) || (x < 0)) { printf ("error"); break; };
        printf("Give me another number : ");
        if ((scanf("%u", &y) != 1) || (y < 0)) { printf ("error"); break; };
        printf("The bigger number is %u\n\n", big (x, y));
    }
    return 1;
}

There seems to be a problem with what I wrote. The function big() is giving wrong output when x == 1 && y == 0 . Why is it not working and how can it be made to work?


Solution

  • You can start the comparison with the highest bits:

    unsigned int big(unsigned int x, unsigned int y)
    {
        for (unsigned int m = ~((unsigned int)-1 >> 1); m; m >>= 1) 
        {
            unsigned int bit_x = x & m;
            unsigned int bit_y = y & m;
            if (bit_x) 
              { if (!bit_y) return x; }
            else if (bit_y) return y;
        }
        return x;
    }
    

    If only shifts and comparisons are allowed:

    unsigned int big(unsigned int x, unsigned int y)
    {
        unsigned int xx = x, yy = y;
        for (;;) 
        {
            if (xx == 0) return y;
            if (yy == 0) return x;
            unsigned int new_xx = xx << 1;
            unsigned int new_yy = yy << 1;
            unsigned int hi_bit_x = (new_xx >> 1) != xx;
            unsigned int hi_bit_y = (new_yy >> 1) != yy;
            if (hi_bit_x) 
              { if (!hi_bit_y) return x; }
            else if (hi_bit_y) return y;
            xx = new_xx;
            yy = new_yy;
        }
        return x;
    }