Thread: A Problem About Usage of Bitwise Operator &

  1. #1
    Registered User
    Join Date
    Jul 2012
    Location
    Ankara
    Posts
    52

    Question A Problem About Usage of Bitwise Operator &

    I can't solve how the program works lowermost. Maybe, I could it, but I may not notice to know the true solution, or I'm not sure.

    For example, I entered number 12, after I ran the program:

    Number 12 is 00000000 00000000 00000000 00001100.
    displayMask is 10000000 00000000 00000000 00000000.

    I can see that expression inside for statement.
    Code:
            putchar(value&displayMask ? '1' : '0');
            value = value << 1;
    I know that;
    1 & 0 = 0
    1 & 1 = 1
    0 & 0 = 0
    0 & 1 = 0.

    But, there isn't just a single number, and isn't just a single comparison in the program. There are 32 numbers and comparisons.(According to my studying book, it says unsigned integers are always stored in 32bits(4bytes) of memory.)

    Question 1: Does the compiler implement processing operator & between 12 and 10000000 00000000 00000000 00000000?

    Question 2:Or does it implement this processing between 00000000 00000000 00000000 00001100 and 10000000 00000000 00000000 00000000?

    Question 1.a: If you say yes for question1, then how can be handled this processing with the operator &? (12 & 100000000 ...)

    Question 2.a: If you say no for question1 and yes for question2, then how can be handled the comparisons of the all numbers?(Meanwhile, if you say yes for question2, then it means that the compiler has already known 'its value in binary system' of '12 in decimal system' ?)

    Question 3: Does the compiler know that it needs binary base of unsigned integer numbers to comparison variables with & ? If yes, so how can we print to output situtation in binary system of any numbers by avoiding indirect way as the expression putchar(value&displayMask ? '1' : '0'); ?


    A Problem About Usage of Bitwise Operator &amp;-output_bitwise-jpg

    Code:
    #include <stdio.h>
    #include <stdlib.h>
    
    void displayBits(unsigned);
    
    int main()
    {
        unsigned x;
        
        printf("Enter a value: ");
        scanf("%u",&x);
        
        displayBits(x);
        
        return 0;
    }
    
    void displayBits(unsigned value)
    {
        unsigned c;
        unsigned displayMask = 1 << 31;
        
        printf("\n%10u = ",value);
        
        for(c=1;c<=32;c++){
            putchar(value&displayMask ? '1' : '0');
            value = value << 1;
        
            if(c%8 == 0){
                putchar(' ');
            }
        }
        putchar('\n');
    }
    Last edited by hefese; 08-16-2012 at 09:45 AM. Reason: grammatical errors

  2. #2
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by hefese
    But, there isn't just a single number, and isn't just a single comparison in the program. There are 32 numbers and comparisons.
    If you want to understand the bitwise and of two 32-bit integers as the and operation applied to each of the corresponding 32 bits, then there are 32 operations (or comparisons). However, the fact remains that this is just one operation involving two integer values.

    Quote Originally Posted by hefese
    According to my studying book, it says unsigned integers are always stored in 32bits(4bytes) of memory.
    Your book is not correct. An "unsigned integer" can mean one of several different unsigned integer types (e.g., unsigned int, unsigned long), and they are not required to be exactly 32 bits in size.

    Quote Originally Posted by hefese
    Question 1: Does the compiler implement processing operator & between 12 and 10000000 00000000 00000000 00000000?

    Question 2:Or does it implement this processing between 00000000 00000000 00000000 00001100 and 10000000 00000000 00000000 00000000?

    Question 1.a: If you say yes for question1, then how can be handled this processing with the operator &? (12 & 100000000 ...)

    Question 2.a: If you say no for question1 and yes for question2, then how can be handled the comparisons of the all numbers?(Meanwhile, if you say yes for question2, then it means that the compiler has already known 'its value in binary system' of '12 in decimal system' ?)
    I don't understand what you mean by the above questions. The compiler translates the operations in C to assembly code (or machine code, or first to some intermediate language). For an unsigned integer, 12 and 00000000 00000000 00000000 00001100 are exactly the same thing, except for representation.

    Quote Originally Posted by hefese
    Question 3: Does the compiler know that it needs binary base of unsigned integer numbers to comparison variables with & ?
    Yes, in the sense that this is how bitwise and is defined. It is bitwise, and a bit is a "digit" in binary.

    Quote Originally Posted by hefese
    If yes, so how can we print to output situtation in binary system of any numbers by avoiding indirect way as the expression putchar(value&displayMask ? '1' : '0'); ?
    There is no standard format specifier for printf that will format in binary, so this "indirect way" is the way to go.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  3. #3
    Registered User
    Join Date
    Jul 2012
    Location
    Ankara
    Posts
    52
    Quote Originally Posted by laserlight View Post
    If you want to understand the bitwise and of two 32-bit integers as the and operation applied to each of the corresponding 32 bits, then there are 32 operations (or comparisons). However, the fact remains that this is just one operation involving two integer values.
    I still don't understand that statement putchar prints just one digit(bit) at once, although there are 32 results due to value&displayMask.


    00000000 00000000 00000000 00001100 = > 32 digits
    10000000 00000000 00000000 00000000 = > 32 digits
    &------------------------------------------- => 32 comparisons
    00000000 00000000 00000000 00000000 = > 32 results.

    I could not mean to properly,clearly at the earlier post. There are 32 results. But it is printed as one bit with putchar statement once. I guess the compiler ignores 31 results each time. But How does the compiler decide to choose which results that putchar prints one bit each time?

    Quote Originally Posted by laserlight View Post
    I don't understand what you mean by the above questions. The compiler translates the operations in C to assembly code (or machine code, or first to some intermediate language). For an unsigned integer, 12 and 00000000 00000000 00000000 00001100 are exactly the same thing, except for representation.
    Actually you answered my questions.


    Quote Originally Posted by laserlight View Post
    There is no standard format specifier for printf that will format in binary, so this "indirect way" is the way to go.
    OK.

    Thank you for answers.

  4. #4
    Registered User
    Join Date
    Jun 2011
    Posts
    4,513
    I think you're misunderstanding what the code is actually doing. The actual result of the & statement is a single result; i.e.

    Code:
    Example with decimal addition:
    
    123  // three digits
    321  // three digits
    ---  // (addition)
    444  // one result
    The code is using a shifting technique to check the value of each binary place and print out the corresponding bit value. It compares against a fixed value with the MSB set. The value under test is shifted (and the result printed each iteration) to produce the binary representation. It's not a direct binary print, but just a clever way of producing equivalent results.

    Just take the code step by step. If you can follow this example, you'll understand how the "putchar()" statement in your code is working:

    Code:
    Lets assume one byte for simplicity:
    
    Value =  12 = 0x0C
    bMask = 128 = 0x80
    
    ----------
    
    Run 1:
    
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0000 1100
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 2:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0001 1000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 3:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0011 0000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 4:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0110 0000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 5:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 1100 0000
    bMask: 1000 0000
    &      ---------
           1000 0000 = true = 1 (print this value)
    
    Run 6:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 1000 0000
    bMask: 1000 0000
    &      ---------
           1000 0000 = true = 1 (print this value)
    
    Run 7:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0000 0000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 8:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0000 0000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    
    // End result = 0000 1100 = 0x0C = 12
    Last edited by Matticus; 08-16-2012 at 01:31 PM.

  5. #5
    Algorithm Dissector iMalc's Avatar
    Join Date
    Dec 2005
    Location
    New Zealand
    Posts
    6,318
    displayMask has only one bit set in it on purpose, it's so that the rest of the bits are ignored (set to zero) as far as the rsult is concerned. Thus each of the 32 results hinges solely on the bit from value in the same position. You'll note that the bits in value shift along to the left by one place each time through the loop as well. This is critical so that a different bit is in the same place as the bit in displayMask each time.
    Make sense?
    My homepage
    Advice: Take only as directed - If symptoms persist, please see your debugger

    Linus Torvalds: "But it clearly is the only right way. The fact that everybody else does it some other way only means that they are wrong"

  6. #6
    Registered User
    Join Date
    Jul 2012
    Location
    Ankara
    Posts
    52
    Quote Originally Posted by Matticus View Post
    I think you're misunderstanding what the code is actually doing. The actual result of the & statement is a single result; i.e.

    Code:
    Example with decimal addition:
    
    123  // three digits
    321  // three digits
    ---  // (addition)
    444  // one result
    The code is using a shifting technique to check the value of each binary place and print out the corresponding bit value. It compares against a fixed value with the MSB set. The value under test is shifted (and the result printed each iteration) to produce the binary representation. It's not a direct binary print, but just a clever way of producing equivalent results.

    Just take the code step by step. If you can follow this example, you'll understand how the "putchar()" statement in your code is working:

    Code:
    Lets assume one byte for simplicity:
    
    Value =  12 = 0x0C
    bMask = 128 = 0x80
    
    ----------
    
    Run 1:
    
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0000 1100
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 2:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0001 1000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 3:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0011 0000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 4:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0110 0000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 5:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 1100 0000
    bMask: 1000 0000
    &      ---------
           1000 0000 = true = 1 (print this value)
    
    Run 6:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 1000 0000
    bMask: 1000 0000
    &      ---------
           1000 0000 = true = 1 (print this value)
    
    Run 7:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0000 0000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    Run 8:
    
    // value = value << 1;
    // putchar(value&displayMask ? '1' : '0');
    
    Value: 0000 0000
    bMask: 1000 0000
    &      ---------
           0000 0000 = false = 0 (print this value)
    
    
    // End result = 0000 1100 = 0x0C = 12
    When I read your posts, I noticed that I didn't read laserlight's posts enough well. Thank you Matticus for representation of the processing &. It was very helpful for me to understand.


    Quote Originally Posted by iMalc View Post
    displayMask has only one bit set in it on purpose, it's so that the rest of the bits are ignored (set to zero) as far as the rsult is concerned. Thus each of the 32 results hinges solely on the bit from value in the same position. You'll note that the bits in value shift along to the left by one place each time through the loop as well. This is critical so that a different bit is in the same place as the bit in displayMask each time.
    Make sense?
    I guess so. Thank you iMalc for your explanation.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Difference between mod and bitwise And operator
    By Swoorup in forum C++ Programming
    Replies: 8
    Last Post: 06-18-2012, 09:56 AM
  2. bitwise operator
    By donkey_C in forum C Programming
    Replies: 7
    Last Post: 09-26-2010, 02:47 PM
  3. Bitwise Operator Help
    By ggraz in forum C Programming
    Replies: 2
    Last Post: 09-28-2008, 09:20 AM
  4. what does this mean, bitwise operator
    By InvariantLoop in forum C++ Programming
    Replies: 11
    Last Post: 03-09-2006, 07:43 PM
  5. bitwise operator
    By ssharish2005 in forum C Programming
    Replies: 8
    Last Post: 09-30-2005, 01:17 AM

Tags for this Thread