Problem with Bit operations

Discussion in 'C Programming' started by alice, Dec 27, 2005.

  1. alice

    alice Guest

    Hi,
    Please look at the following program:

    int main(void)
    {
    char c;
    c = -16;

    if(c & (0x1<<7) !=0)
    printf("TRUE\n");
    else
    printf("FALSE\n");

    return 0;
    }

    The above program should print TRUE ( as -128 is not equal to 0) but
    the above program is printing FALSE. Can anybody please tell why it is
    so?

    PS It is NOT a homework. I'm using the above concept in initializing
    the bits for the Block Bitmap.
     
    alice, Dec 27, 2005
    #1
    1. Advertising

  2. alice

    Artie Gold Guest

    alice wrote:
    > Hi,
    > Please look at the following program:
    >
    > int main(void)
    > {
    > char c;


    Whether `char' is signed or unsigned is system dependent (and a type
    distinct from `unsigned char' or `signed char' as well). If you are
    going to assign a negative number to it, it would be better to make it
    explicitly signed.

    > c = -16;
    >
    > if(c & (0x1<<7) !=0)

    ITYM:
    if ((c & (0x1 << 7)) != 0)

    [!= binds more tightly than &]

    > printf("TRUE\n");
    > else
    > printf("FALSE\n");
    >
    > return 0;
    > }
    >
    > The above program should print TRUE ( as -128 is not equal to 0) but
    > the above program is printing FALSE. Can anybody please tell why it is
    > so?
    >


    HTH,
    --ag
    --
    Artie Gold -- Austin, Texas
    http://goldsays.blogspot.com
    http://www.cafepress.com/goldsays
    "If you have nothing to hide, you're not trying!"
     
    Artie Gold, Dec 27, 2005
    #2
    1. Advertising

  3. In article <>,
    alice <> wrote:
    >Please look at the following program:


    > int main(void)
    >{
    > char c;
    > c = -16;


    In C, it is up to the compiler writers to decide whether a plain
    "char" variable is "signed" or "unsigned".

    If, on your implementation, "char" is signed, then then assignment will
    store the -numeric- value you are expecting... but not necessarily the
    bit pattern you are expecting.

    If, on your implementation, "char" is unsigned, then you would
    have an implicit signed-to-unsigned conversion going on. The value
    stored would be UCHAR_MAX + 1 - 16; i.e., 240 for the common case
    of UCHAR_MAX being 255.


    > if(c & (0x1<<7) !=0)
    > printf("TRUE\n");
    > else
    > printf("FALSE\n");
    >
    > return 0;
    >}


    >The above program should print TRUE ( as -128 is not equal to 0) but
    >the above program is printing FALSE. Can anybody please tell why it is
    >so?


    You are counting on a particular bit representation for a negative
    value, but C allows implementations to choose from three different
    bit representation for negative values. The most common representation
    is "twos complement" (-x is 1 plus the bitwise complement of x,
    +0 and -0 are the same), but C also allows "ones complement"
    (-x is the bitwise complement of x, +0 is "all bits clear", -0 is
    "all bits set"), and "signed magnitude" (there is a bit which
    does nothing other than hold the sign of the value, and -x has
    the same value bits as x but with the sign bit changed.)

    Notice that in "signed magnitude" representation in which
    a total of 8 bits are stored per character, 1<<7 is outside
    the representable positive range (which only uses 7 bits for value)
    and so would overflow with undefined results
    (most likely that 1<<7 would be 0.)

    Notice that in 2s complement signed character representation in which 8
    bits are stored per character, 1<<7 would try to represent +128 but
    that +127 is the largest possible positive number in that
    situation, so the behaviour would be undefined.


    I notice that you have used 0x1<<7 instead of 1<<7 . That
    suggest to me that you might be thinking that somehow using
    the 0x notation indicates an unsigned value. That is not the
    case, though: 0x notation merely indicates hexidecimal representation.


    If you want to work at the bit level, you should not
    *assume* that you are on a 2s complement machine (but it
    might be fair to -test- to see if you are, and to abort
    the program if you are not.)

    You should never assume that char is signed or unsigned.
    If you want signed or unsigned char, then code
    "signed char" or "unsigned char" explicitly.

    When you are working at the bit level, working with signed
    values can lead to unexpected results unless you know exactly
    what the rules are. If you want to work at the bit level, you
    should probably only work with unsigned quantities.

    Also, you should not assume that manipulation of literal constants
    (such as 1<<7) is working with unsigned values. You should instead
    take the care to use the appropriate suffix to indicate that you
    want the unsigned version of the constant. For example, 1U << 7
    --
    All is vanity. -- Ecclesiastes
     
    Walter Roberson, Dec 27, 2005
    #3
  4. alice

    Joe Wright Guest

    alice wrote:
    > Hi,
    > Please look at the following program:
    >
    > int main(void)
    > {
    > char c;
    > c = -16;
    >
    > if(c & (0x1<<7) !=0)
    > printf("TRUE\n");
    > else
    > printf("FALSE\n");
    >
    > return 0;
    > }
    >
    > The above program should print TRUE ( as -128 is not equal to 0) but
    > the above program is printing FALSE. Can anybody please tell why it is
    > so?
    >
    > PS It is NOT a homework. I'm using the above concept in initializing
    > the bits for the Block Bitmap.
    >

    The expression you are testing is of type int. c is converted to int as

    0xfffffff0 and or course 0x1 << 7 looks like..
    0x00000080 and anding them results in..
    0x00000080 which is != 0 and therefore FALSE.

    --
    Joe Wright
    "Everything should be made as simple as possible, but not simpler."
    --- Albert Einstein ---
     
    Joe Wright, Dec 27, 2005
    #4
  5. alice

    haroon Guest

    alice wrote:
    > Hi,
    > Please look at the following program:


    [...]

    > if(c & (0x1<<7) !=0)


    > The above program should print TRUE ( as -128 is not equal to 0) but


    [...]

    try this
    /****/
    if((c & (0x1<<7)) !=0)
    /****/

    precedence of != operator is higher.
     
    haroon, Dec 28, 2005
    #5
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Sanket Suryawanshi

    bit operations in Java

    Sanket Suryawanshi, Jan 23, 2004, in forum: Java
    Replies:
    3
    Views:
    7,102
    Jon A. Cruz
    Jan 23, 2004
  2. Jesus M. Salvo Jr.
    Replies:
    2
    Views:
    4,306
    robert
    Feb 11, 2006
  3. Replies:
    3
    Views:
    1,830
    Timothy Bendfelt
    Jan 19, 2007
  4. Replies:
    9
    Views:
    1,032
    Juha Nieminen
    Aug 22, 2007
  5. Jeff.M
    Replies:
    6
    Views:
    199
    Lasse Reichstein Nielsen
    May 4, 2009
Loading...

Share This Page