bitwise operator !!

Discussion in 'C Programming' started by chang, Dec 7, 2008.

  1. chang

    chang Guest

    Hi .
    I am surprised about this C Question answer even i am also not sharp
    in C.

    Programme is -:

    #include<stdio.h>
    void main()
    {
    int a= -3;

    printf("%d",a>>1);
    }

    Here the printf value is coming :-2.
    How come here the value is coming is -2. Please help me to know what
    is happenning for negative value(a= -3).

    Thanks for advance

    Chang
     
    chang, Dec 7, 2008
    #1
    1. Advertising

  2. chang

    Guest

    On Dec 7, 4:21 am, chang <> wrote:
    > Hi .
    >  I am surprised about this C Question answer even i am also not sharp
    > in C.
    >
    > Programme is -:
    >
    > #include<stdio.h>
    > void main()
    > {
    >         int a= -3;
    >
    >         printf("%d",a>>1);
    >
    > }
    >
    > Here the printf value is coming :-2.
    > How come here the value is coming is -2. Please help me to know what
    > is happenning for negative value(a= -3).


    It depends on how your machine stores negative numbers. If your
    machine is like mine, the 32-bit integer -3 will look like this in
    binary:

    11111111111111111111111111111101

    Then you perform a right shift on this integer. Shifting right a
    negative (signed) integer is generally a bad idea because it's
    implementation-defined whether 0's or 1's are added to the left. If
    your machine is like mine, this right shift will add a 1 bit to the
    left, and the resulting integer will look like this:

    11111111111111111111111111111110

    And that is -2 in decimal.

    Sebastian
     
    , Dec 7, 2008
    #2
    1. Advertising

  3. chang

    chang Guest

    On Dec 7, 2:58 pm, wrote:
    > On Dec 7, 4:21 am, chang <> wrote:
    >
    >
    >
    >
    >
    > > Hi .
    > >  I am surprised about this C Question answer even i am also not sharp
    > > in C.

    >
    > > Programme is -:

    >
    > > #include<stdio.h>
    > > void main()
    > > {
    > >         int a= -3;

    >
    > >         printf("%d",a>>1);

    >
    > > }

    >
    > > Here the printf value is coming :-2.
    > > How come here the value is coming is -2. Please help me to know what
    > > is happenning for negative value(a= -3).

    >
    > It depends on how your machine stores negative numbers. If your
    > machine is like mine, the 32-bit integer -3 will look like this in
    > binary:
    >
    > 11111111111111111111111111111101
    >
    > Then you perform a right shift on this integer. Shifting right a
    > negative (signed) integer is generally a bad idea because it's
    > implementation-defined whether 0's or 1's are added to the left. If
    > your machine is like mine, this right shift will add a 1 bit to the
    > left, and the resulting integer will look like this:
    >
    > 11111111111111111111111111111110
    >
    > And that is -2 in decimal.
    >
    > Sebastian- Hide quoted text -
    >
    > - Show quoted text -



    hi
    Thanks all.

    I got this idea but why this kind of system is there: -1
    representating in this format 11111111111111111111111111111111?
    Actually what is defination lies in this?

    Thanks
    Chang
     
    chang, Dec 7, 2008
    #3
  4. chang

    Willem Guest

    chang wrote:
    ) I got this idea but why this kind of system is there: -1
    ) representating in this format 11111111111111111111111111111111?
    ) Actually what is defination lies in this?

    Simple. Look at this calculation of zero minus one, in binary.
    (I use 4 bits to keep it simple)

    0000
    0001 -
    ----
    1 (carry the one)

    0000
    0001 -
    1 (this is the carry)
    ----
    11 (carry the one again)

    0000
    0001 -
    1 (this is the carry)
    ----
    111 (carry the one again)

    0000
    0001 -
    1 (this is the carry)
    ----
    1111 (carry the one again)

    0000
    0001 -
    1 (this carry can't be used, it's a so-called carry overflow)
    ----
    1111

    So, the result of zero minus one, in binary, is a row of '1' bits.

    (From this, it should be easy to determine what -2 is in binary.)


    SaSW, Willem
    --
    Disclaimer: I am in no way responsible for any of the statements
    made in the above text. For all I know I might be
    drugged or something..
    No I'm not paranoid. You all think I'm paranoid, don't you !
    #EOT
     
    Willem, Dec 7, 2008
    #4
  5. chang

    chang Guest

    On Dec 7, 3:44 pm, Willem <> wrote:
    > chang wrote:
    >
    > ) I got this idea but why this kind of system is there: -1
    > ) representating in this format 11111111111111111111111111111111?
    > ) Actually what is defination lies in this?
    >
    > Simple.  Look at this calculation of zero minus one, in binary.
    > (I use 4 bits to keep it simple)
    >
    >   0000
    >   0001 -
    >   ----
    >      1 (carry the one)
    >
    >   0000
    >   0001 -
    >     1  (this is the carry)
    >   ----
    >     11 (carry the one again)
    >
    >   0000
    >   0001 -
    >    1  (this is the carry)
    >   ----
    >    111 (carry the one again)
    >
    >   0000
    >   0001 -
    >   1  (this is the carry)
    >   ----
    >   1111 (carry the one again)
    >
    >   0000
    >   0001 -
    >  1     (this carry can't be used, it's a so-called carry overflow)
    >   ----
    >   1111
    >
    > So, the result of zero minus one, in binary, is a row of '1' bits.
    >
    > (From this, it should be easy to determine what -2 is in binary.)
    >
    > SaSW, Willem
    > --
    > Disclaimer: I am in no way responsible for any of the statements
    >             made in the above text. For all I know I might be
    >             drugged or something..
    >             No I'm not paranoid. You all think I'm paranoid, don't you !
    > #EOT



    Thanks .

    But i am actually looking for why (-1) is represented as 0XFFFFFFFF or
    in binary all bits will be 1!!!


    Please guide me to know about this.

    Chang
     
    chang, Dec 7, 2008
    #5
  6. chang

    Bartc Guest

    chang wrote:
    > On Dec 7, 3:44 pm, Willem <> wrote:
    >> chang wrote:
    >>
    >> ) I got this idea but why this kind of system is there: -1
    >> ) representating in this format 11111111111111111111111111111111?
    >> ) Actually what is defination lies in this?
    >>
    >> Simple. Look at this calculation of zero minus one, in binary.
    >> (I use 4 bits to keep it simple)
    >>
    >> 0000
    >> 0001 -
    >> ----
    >> 1 (carry the one)

    .....
    >> 0000
    >> 0001 -
    >> 1 (this carry can't be used, it's a so-called carry overflow)
    >> ----
    >> 1111
    >>
    >> So, the result of zero minus one, in binary, is a row of '1' bits.
    >>
    >> (From this, it should be easy to determine what -2 is in binary.)
    >>
    >> SaSW, Willem
    >> --
    >> Disclaimer: I am in no way responsible for any of the statements
    >> made in the above text. For all I know I might be
    >> drugged or something..
    >> No I'm not paranoid. You all think I'm paranoid, don't you !
    >> #EOT

    >
    >
    > Thanks .
    >
    > But i am actually looking for why (-1) is represented as 0XFFFFFFFF or
    > in binary all bits will be 1!!!


    Didn't Willem just explain exactly that?

    Try adding binary 000...001 to your row of 1 bits. You should get all zeros.
    The same as adding 1 to -1. So -1 and all 1s are equivalent in that
    encoding.

    The same sometimes occurs in decimal. You might remember the old-fashioned
    tape counters, which when you rewound would show 002, 001, 000, 999, ...
    where you might have expected 002, 001, 000, -001,... But adding 001 to 999
    gives 000, so it must be right!

    --
    Bartc
     
    Bartc, Dec 7, 2008
    #6
  7. On Dec 7, 4:03 pm, chang <> wrote:
    > On Dec 7, 3:44 pm, Willem <> wrote:
    >
    >
    >
    > > chang wrote:

    >
    > > ) I got this idea but why this kind of system is there: -1
    > > ) representating in this format 11111111111111111111111111111111?
    > > ) Actually what is defination lies in this?

    >
    > > Simple.  Look at this calculation of zero minus one, in binary.
    > > (I use 4 bits to keep it simple)

    >
    > >   0000
    > >   0001 -
    > >   ----
    > >      1 (carry the one)

    >
    > >   0000
    > >   0001 -
    > >     1  (this is the carry)
    > >   ----
    > >     11 (carry the one again)

    >
    > >   0000
    > >   0001 -
    > >    1  (this is the carry)
    > >   ----
    > >    111 (carry the one again)

    >
    > >   0000
    > >   0001 -
    > >   1  (this is the carry)
    > >   ----
    > >   1111 (carry the one again)

    >
    > >   0000
    > >   0001 -
    > >  1     (this carry can't be used, it's a so-called carry overflow)
    > >   ----
    > >   1111

    >
    > > So, the result of zero minus one, in binary, is a row of '1' bits.

    >
    > > (From this, it should be easy to determine what -2 is in binary.)

    >
    > > SaSW, Willem
    > > --
    > > Disclaimer: I am in no way responsible for any of the statements
    > >             made in the above text. For all I know I might be
    > >             drugged or something..
    > >             No I'm not paranoid. You all think I'm paranoid, don't you !
    > > #EOT

    >
    > Thanks .
    >
    > But i am actually looking for why (-1) is represented as 0XFFFFFFFF or
    > in binary all bits will be  1!!!
    >
    > Please guide me to know about this.
    >
    > Chang


    http://en.wikipedia.org/wiki/Two's_complement
     
    Sri Harsha Dandibhotla, Dec 7, 2008
    #7
  8. chang <> writes:

    > On Dec 7, 3:44 pm, Willem <> wrote:
    >> chang wrote:
    >>
    >> ) I got this idea but why this kind of system is there: -1
    >> ) representating in this format 11111111111111111111111111111111?
    >> ) Actually what is defination lies in this?
    >>
    >> Simple.  Look at this calculation of zero minus one, in binary.
    >> (I use 4 bits to keep it simple)
    >>
    >>   0000
    >>   0001 -
    >>   ----
    >>      1 (carry the one)
    >>
    >>   0000
    >>   0001 -
    >>     1  (this is the carry)
    >>   ----
    >>     11 (carry the one again)
    >>
    >>   0000
    >>   0001 -
    >>    1  (this is the carry)
    >>   ----
    >>    111 (carry the one again)
    >>
    >>   0000
    >>   0001 -
    >>   1  (this is the carry)
    >>   ----
    >>   1111 (carry the one again)
    >>
    >>   0000
    >>   0001 -
    >>  1     (this carry can't be used, it's a so-called carry overflow)
    >>   ----
    >>   1111
    >>
    >> So, the result of zero minus one, in binary, is a row of '1' bits.
    >>
    >> (From this, it should be easy to determine what -2 is in binary.)
    >>
    >> SaSW, Willem
    >> --


    Best not to quote sigs (the part after the "-- ").

    > Thanks .
    >
    > But i am actually looking for why (-1) is represented as 0XFFFFFFFF or
    > in binary all bits will be 1!!!


    That is what Willem was doing. Let me try another way (the is related
    to his example). We want -1 + 1 == 0, yes? What happens to "all
    ones" when we add one?

    --
    Ben.
     
    Ben Bacarisse, Dec 7, 2008
    #8
  9. chang

    CBFalconer Guest

    chang wrote:
    >
    > I am surprised about this C Question answer even i am also not
    > sharp in C.
    >
    > #include<stdio.h>
    > void main() {
    > int a= -3;
    > printf("%d",a>>1);
    > }
    >
    > Here the printf value is coming :-2.
    > How come here the value is coming is -2. Please help me to know
    > what is happenning for negative value(a= -3).


    Attempting to shift a negative value results in either
    implementation or undefined behaviour. Don't ever apply the shift
    operator to a negative value. You may use division, however.

    --
    [mail]: Chuck F (cbfalconer at maineline dot net)
    [page]: <http://cbfalconer.home.att.net>
    Try the download section.
     
    CBFalconer, Dec 8, 2008
    #9
  10. chang

    Bartc Guest

    "CBFalconer" <> wrote in message
    news:...
    > chang wrote:
    >>
    >> I am surprised about this C Question answer even i am also not
    >> sharp in C.
    >>
    >> #include<stdio.h>
    >> void main() {
    >> int a= -3;
    >> printf("%d",a>>1);
    >> }
    >>
    >> Here the printf value is coming :-2.
    >> How come here the value is coming is -2. Please help me to know
    >> what is happenning for negative value(a= -3).

    >
    > Attempting to shift a negative value results in either
    > implementation or undefined behaviour. Don't ever apply the shift
    > operator to a negative value. You may use division, however.


    Apparently division of negative values is also implementation defined (in
    C90).

    -3/2 can be either -2 or -1.

    --
    Bartc
     
    Bartc, Dec 8, 2008
    #10
  11. "Jujitsu Lizard" <> writes:

    > "chang" <> wrote in message
    > news:...
    >> Hi .
    >> I am surprised about this C Question answer even i am also not sharp
    >> in C.
    >>
    >> Programme is -:
    >>
    >> #include<stdio.h>
    >> void main()
    >> {
    >> int a= -3;
    >>
    >> printf("%d",a>>1);
    >> }
    >>
    >> Here the printf value is coming :-2.
    >> How come here the value is coming is -2. Please help me to know what
    >> is happenning for negative value(a= -3).

    >
    > The other posters in this newsgroup are knuckleheads who don't
    > understand C, computing in general, or digital logic design.


    I'll bear that in mind!

    > Let me help you out here.

    <snip>
    > Need to shift a signed number right 5 bits?
    >
    > if (x<0)
    > {
    > result = (x >> 5) | (-1 << (sizeof(int) * 8 - 5);


    You have turned simple implementation-defined behaviour into undefined
    behaviour. How is that helping the OP?

    > }
    > else
    > {
    > result = ((unsigned)(x)) >> 5;


    What is the point of that cast?

    > }


    --
    Ben.
     
    Ben Bacarisse, Dec 8, 2008
    #11
  12. chang

    CBFalconer Guest

    Jujitsu Lizard wrote:
    > "Bartc" <> wrote in message
    >

    .... snip ...
    >
    >> Apparently division of negative values is also implementation
    >> defined (in C90).
    >>
    >> -3/2 can be either -2 or -1.

    >
    > You've gotta be fecal mattering me. Got a citation for that?
    > That seems absurd.


    Corrected for C99.

    --
    [mail]: Chuck F (cbfalconer at maineline dot net)
    [page]: <http://cbfalconer.home.att.net>
    Try the download section.
     
    CBFalconer, Dec 8, 2008
    #12
  13. chang

    CBFalconer Guest

    Jujitsu Lizard wrote:
    >

    .... snip ...
    >
    > The other posters in this newsgroup are knuckleheads who don't
    > understand C, computing in general, or digital logic design.
    > Let me help you out here.
    >
    > Two's complement representation evolved so that people could use
    > the same instructions on signed as on unsigned operands (it is a
    > digital logic thing). If you work through examples carefully,
    > you'll see that an adder that works for signed quantities works
    > just fine for 2's complement quantities as well. All that
    > differs is flags and branches.


    C does not insist on 2's complement. 1's complement, and
    sign-magnitude are also completely legal. You can't use shifts on
    negative quantities.

    --
    [mail]: Chuck F (cbfalconer at maineline dot net)
    [page]: <http://cbfalconer.home.att.net>
    Try the download section.
     
    CBFalconer, Dec 8, 2008
    #13
  14. "Jujitsu Lizard" <> writes:

    > "Bartc" <> wrote in message
    > news:W6__k.3191$...
    >> "CBFalconer" <> wrote in message
    >> news:...
    >>> chang wrote:
    >>>>
    >>>> I am surprised about this C Question answer even i am also not
    >>>> sharp in C.
    >>>>
    >>>> #include<stdio.h>
    >>>> void main() {
    >>>> int a= -3;
    >>>> printf("%d",a>>1);
    >>>> }
    >>>>
    >>>> Here the printf value is coming :-2.
    >>>> How come here the value is coming is -2. Please help me to know
    >>>> what is happenning for negative value(a= -3).
    >>>
    >>> Attempting to shift a negative value results in either
    >>> implementation or undefined behaviour. Don't ever apply the shift
    >>> operator to a negative value. You may use division, however.

    >>
    >> Apparently division of negative values is also implementation
    >> defined (in C90).
    >>
    >> -3/2 can be either -2 or -1.

    >
    > You've gotta be fecal mattering me. Got a citation for that? That
    > seems absurd.


    3.3.5 Multiplicative Operators

    "If either operand is negative, whether the result of the / operator is
    the largest integer less than the algebraic quotient or the smallest
    integer greater than the algebraic quotient is implementation-defined,
    as is the sign of the result of the % operator."

    C99 altered this to require a particular choice.

    6.5.5 (6) "When integers are divided, the result of the / operator is
    the algebraic quotient with any fractional part discarded."

    So in C99, -3/2 == -1.

    There was a discussion on this very topic on this group just a couple
    weeks ago. I can't find it in my spool just now but Google Groups
    should be able to. Basically the issue is that different machines have
    divide instructions which work in different ways on negative numbers,
    and C90 wanted to allow division to use the native instruction in all
    cases. (Note for example that on a 16-bit machine with two's complement
    arithmetic, you might expect to divide a signed integer by 2 by shifting
    right by one bit, shifting in a sign bit on the left. -3 = 0xfffd,
    which when shifted right gives 0xfffe = -2.) This variance was
    apparently found to be inconvenient, so C99 might require some machines
    to use multiple instructions (maybe a conditional jump) to get the right
    behavior.
     
    Nate Eldredge, Dec 8, 2008
    #14
  15. chang

    James Kuyper Guest

    Jujitsu Lizard wrote:
    > "Bartc" <> wrote in message
    > news:W6__k.3191$...

    ....
    >> Apparently division of negative values is also implementation defined
    >> (in C90).
    >>
    >> -3/2 can be either -2 or -1.

    >
    > You've gotta be fecal mattering me. Got a citation for that? That
    > seems absurd.


    I don't have a citation, because I don't have a copy of the C90
    standard. However, I can explain why this was the case. There are
    arguments for having either -2 or -1 as a result for -3/2. At the time
    the C89 standard was written, there were many implementations that would
    produce -2, and many others where it would produce -1. The standard was
    therefore written to accommodate both choices.

    If it's any consolation, this was changed in C99. A result of -1 is now
    required. For most of my code, a value of -2 would have been better
    (mainly because of what it implies for the % operator). However, having
    a single required result, even if it's the "wrong" one from my point of
    view, makes things easier than having two different possible results.
     
    James Kuyper, Dec 8, 2008
    #15
  16. "Jujitsu Lizard" <> writes:

    > "Ben Bacarisse" <> wrote in message
    > news:...
    >>>
    >>> The other posters in this newsgroup are knuckleheads who don't
    >>> understand C, computing in general, or digital logic design.

    >>
    >> I'll bear that in mind!

    >
    > You should, because you're one of them!


    I assumed so. You made no exception to the rule.

    >>> Let me help you out here.

    >> <snip>
    >>> Need to shift a signed number right 5 bits?
    >>>
    >>> if (x<0)
    >>> {
    >>> result = (x >> 5) | (-1 << (sizeof(int) * 8 - 5);

    >>
    >> You have turned simple implementation-defined behaviour into undefined
    >> behaviour. How is that helping the OP?

    >
    > Your job as my antagonist is to show how it is undefined. (BTW, I'm
    > missing a closing parenthesis, I think). What don't you understand?
    > What do you believe is undefined?


    Shifting a signed integer to the left.

    >>> }
    >>> else
    >>> {
    >>> result = ((unsigned)(x)) >> 5;

    >>
    >> What is the point of that cast?
    >>
    >>> }

    >
    > It is called "casting symmetry". If you have an if-else construct and
    > a cast occurs in the if() part, there must also be at least one cast
    > in the else part. (Translation: you are probably right.)


    There is no cast in the other branch of the if. If I accepted your
    symmetry rule (I don't, but that is by the by) you would need to add
    one to the 'if' part.

    --
    Ben.
     
    Ben Bacarisse, Dec 8, 2008
    #16
  17. "Jujitsu Lizard" <> writes:

    > "Ben Bacarisse" <> wrote in message
    > news:...
    >>
    >>>>> Need to shift a signed number right 5 bits?
    >>>>>
    >>>>> if (x<0)
    >>>>> {
    >>>>> result = (x >> 5) | (-1 << (sizeof(int) * 8 - 5);
    >>>>
    >>>> You have turned simple implementation-defined behaviour into undefined
    >>>> behaviour. How is that helping the OP?
    >>>
    >>> Your job as my antagonist is to show how it is undefined. (BTW, I'm
    >>> missing a closing parenthesis, I think). What don't you understand?
    >>> What do you believe is undefined?

    >>
    >> Shifting a signed integer to the left.

    >
    > Hi Ben,
    >
    > I thought that shifting a signed integer to the left was perfectly
    > defined but shifting a signed integer to the right had the bothersome
    > complexity.
    >
    > Am I wrong?


    Yes.

    6.5.7 (4-5) of the C99 standard says (paraphrasing) that a *nonnegative*
    integer of a signed *type* can be shifted left or right with the
    expected result. But if the value of the integer is negative, then "the
    behavior is undefined" in both cases.

    You might want to get yourself a copy of the standard (costs money) or a
    reasonable draft thereof (free) and you can search out these details
    yourself. See http://clc-wiki.net/wiki/The_C_Standard for some links.
     
    Nate Eldredge, Dec 8, 2008
    #17
  18. chang

    CBFalconer Guest

    Jujitsu Lizard wrote:
    > "Ben Bacarisse" <> wrote:
    >

    .... snip ...
    >
    >> Shifting a signed integer to the left.

    >
    > I thought that shifting a signed integer to the left was perfectly
    > defined but shifting a signed integer to the right had the
    > bothersome complexity.
    >
    > Am I wrong?


    Yes. Shifting a negative value left can result in sign changes
    and/or overflow. That is covered in the standard as either
    implementation or undefined behaviour. Don't do that.

    --
    [mail]: Chuck F (cbfalconer at maineline dot net)
    [page]: <http://cbfalconer.home.att.net>
    Try the download section.
     
    CBFalconer, Dec 8, 2008
    #18
  19. chang

    Flash Gordon Guest

    CBFalconer wrote, On 08/12/08 01:35:
    > Jujitsu Lizard wrote:
    > ... snip ...
    >> The other posters in this newsgroup are knuckleheads who don't
    >> understand C, computing in general, or digital logic design.
    >> Let me help you out here.
    >>
    >> Two's complement representation evolved so that people could use
    >> the same instructions on signed as on unsigned operands (it is a
    >> digital logic thing). If you work through examples carefully,
    >> you'll see that an adder that works for signed quantities works
    >> just fine for 2's complement quantities as well. All that
    >> differs is flags and branches.

    >
    > C does not insist on 2's complement. 1's complement, and
    > sign-magnitude are also completely legal. You can't use shifts on
    > negative quantities.


    It can go wrong with 2's complement machines as well. There have been
    processors with only a logical shit.

    However, since the behaviour is implementation defined, you can use it
    as long as you read the implementation documentation to find out *how*
    it is defined for that specific implementation and don't care about
    portability to implementations which define it differently. I don't
    think it is a good idea, but you can do it.
    --
    Flash Gordon
    If spamming me sent it to
    If emailing me use my reply-to address
    See the comp.lang.c Wiki hosted by me at http://clc-wiki.net/
     
    Flash Gordon, Dec 8, 2008
    #19
  20. chang

    Ian Collins Guest

    Flash Gordon wrote:
    >
    > It can go wrong with 2's complement machines as well. There have been
    > processors with only a logical shit.


    :)

    --
    Ian Collins
     
    Ian Collins, Dec 8, 2008
    #20
    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. littlehobo

    Bitwise operator question...

    littlehobo, Sep 30, 2003, in forum: C++
    Replies:
    10
    Views:
    6,045
    Ron Natalie
    Oct 1, 2003
  2. Peter Shaggy Haywood

    Re: bitwise operator on a struct

    Peter Shaggy Haywood, Jun 25, 2003, in forum: C Programming
    Replies:
    0
    Views:
    1,581
    Peter Shaggy Haywood
    Jun 25, 2003
  3. Peter Shaggy Haywood

    Re: bitwise operator on a struct

    Peter Shaggy Haywood, Jun 25, 2003, in forum: C Programming
    Replies:
    0
    Views:
    817
    Peter Shaggy Haywood
    Jun 25, 2003
  4. Manish_Ganvir
    Replies:
    13
    Views:
    1,584
    Keith Thompson
    Feb 14, 2005
  5. Ioannis Vranos
    Replies:
    8
    Views:
    340
    James Kanze
    Nov 14, 2008
Loading...

Share This Page