simple math question

J

John Salerno

Hi all. I'm just starting out with Python, so I'm a little slow right
now. :)

Can someone explain to me why the expression 5 / -2 evaluates to -3,
especially considering that -2 * -3 evaluates to 6?

I'm sure it has something to do with the negative number and the current
way that the / operator is implemented, but why doesn't it evaluate to
-2 instead?
 
F

Felipe Almeida Lessa

Em Sáb, 2006-02-11 às 14:52 -0500, John Salerno escreveu:
Hi all. I'm just starting out with Python, so I'm a little slow right
now. :)

Can someone explain to me why the expression 5 / -2 evaluates to -3,
especially considering that -2 * -3 evaluates to 6?

I'm sure it has something to do with the negative number and the current
way that the / operator is implemented, but why doesn't it evaluate to
-2 instead?

It has to do with floating point operations. If you evaluate 5 / -2.0 or
5.0 / -2 you will have -2.5. It gives you -3 because of rounding to
integers. Look:
3.0

This behavior is because -round(x) should be equal to round(-x).

Cya,
Felipe.

--
"Quem excele em empregar a força militar subjulga os exércitos dos
outros povos sem travar batalha, toma cidades fortificadas dos outros
povos sem as atacar e destrói os estados dos outros povos sem lutas
prolongadas. Deve lutar sob o Céu com o propósito primordial da
'preservação'. Desse modo suas armas não se embotarão, e os ganhos
poderão ser preservados. Essa é a estratégia para planejar ofensivas."

-- Sun Tzu, em "A arte da guerra"
 
J

James Stroud

John said:
Hi all. I'm just starting out with Python, so I'm a little slow right
now. :)

Can someone explain to me why the expression 5 / -2 evaluates to -3,
especially considering that -2 * -3 evaluates to 6?

I'm sure it has something to do with the negative number and the current
way that the / operator is implemented, but why doesn't it evaluate to
-2 instead?

Its an integer expression.

Try '5.0/-2' or '5/-2.0' or 'float(5)/-2' or '5/float(-2)' and compare
'5/-2' to '5/2'.

James
 
R

Rinzwind

'/' is a floor division (1/2 == 0) unless validated by a from
__future__ import division.

So:
5/2=2.5 -> nearest lowest non-decimal number makes it 2.
5/-2=-2.5 -> nearest lowest non-decilmal number makes it -3
 
P

Paul Rubin

John Salerno said:
Can someone explain to me why the expression 5 / -2 evaluates to -3,
especially considering that -2 * -3 evaluates to 6?

I'm sure it has something to do with the negative number and the
current way that the / operator is implemented, but why doesn't it
evaluate to -2 instead?

Well, -2 * -2 is 4, which is not especially better than 6. The
reason for choosing -3 instead of -2 is so that if b is positive,
then a%b is non-negative even if a is negative. That is, the
motivating case is (-5 % 2) which is done the same way as (5 % -2).

You want (b*(a/b) + a%b)==a at all times. If (-5 / 2) = -3, then you
need (-5 % 2) = -1. But if (-5 / 2) = -2, then (-5 % 2) = +1.
Since a%b is positive, you can use it as a list index, etc.
 
T

Terry Reedy

John Salerno said:
Can someone explain to me why the expression 5 / -2 evaluates to -3,
especially considering that -2 * -3 evaluates to 6?

With same sign int division, one can think of the result as either being
rounding down or rounding to zero. With mixed sign int division, rounding
to zero becomes rounding up, so the language designer has to choose being
consistent with one or the other but not both. There are pluses and
minuses either way and different language designers have made different
choices between the two.

Guido's rational was posted some years ago but I forget. You might be able
to find something in Google's c.l.p archives, or on the web in general.

Terry Jan Reedy
 
J

John Salerno

Rinzwind said:
'/' is a floor division (1/2 == 0) unless validated by a from
__future__ import division.

So:
5/2=2.5 -> nearest lowest non-decimal number makes it 2.
5/-2=-2.5 -> nearest lowest non-decilmal number makes it -3

Ah, this makes the most sense to me. -2.5 rounded down is -3. I guess I
was thinking of it more in terms of "-2 goes into 5 -3 times", which is
a little hard to wrap my mind around.
 
J

John Salerno

John said:
Hi all. I'm just starting out with Python, so I'm a little slow right
now. :)

Can someone explain to me why the expression 5 / -2 evaluates to -3,
especially considering that -2 * -3 evaluates to 6?

I'm sure it has something to do with the negative number and the current
way that the / operator is implemented, but why doesn't it evaluate to
-2 instead?

Thanks for the help guys! It's clearer to me now, and I think I was just
conceptualizing it the wrong way in the first place.
 
D

Dan Bishop

Paul said:
Well, -2 * -2 is 4, which is not especially better than 6. The
reason for choosing -3 instead of -2 is so that if b is positive,
then a%b is non-negative even if a is negative. That is, the
motivating case is (-5 % 2) which is done the same way as (5 % -2).

As a more concrete example, consider the case of a Date class that
stores dates as the number of days since an epoch, which happens to be
a Sunday. To compute the day of the week a date falls on, you could
use:

SUNDAY, MONDAY, ..., SATURDAY = xrange(7)

class Date:
...
def weekday(self):
return self.daycount % 7


But what about the day BEFORE the epoch, represented by -1?

Case 1: Suppose that -1 // 7 == 0, as it is in C. In order to preserve
that
You want (b*(a/b) + a%b)==a at all times.

With a=-1, b=7, and a//b=0, this means (7*0 + a%b)==-1, which requires
that -1 % 7 == -1. This doesn't correspond to any of the weekday
constants, which means you'd have to rewrite your weekday() method if
you wanted to handle negative dates.

Case 2: Suppose that -1 // 7 = -1.

Then (7*(-1) + -1%7)==-1, which means -1%7 happens to be 6. This says
that the day before the epoch is a Saturday, which is exactly what you
want.
Since a%b is positive, you can use it as a list index, etc.

This isn't the best explanation, because negative list indices *are*
allowed.
 
D

Dave Hansen

Thanks for the help guys! It's clearer to me now, and I think I was just
conceptualizing it the wrong way in the first place.

Probably not the "wrong" way, just a different way, especially if you
write C code.

The C standard defines integer division as (something like) "the
integer part of the result, throwing away the fraction," which would
get you the value you expect.

This also means the sign of the result of the C % operator matches the
sign of the numerator. In Python, the sign matches the sign of the
denominator.

You could also describe the C scheme as "truncating towards zero."
Python (and my HP calculator) "truncates toward negative infinity." I
suppose a third way to do it would be to "truncate towards positive
infinity," but I don't know of any concrete examples of this. 'Twould
seem counter-intuitive in any case...

Regards,
-=Dave
 
J

John Salerno

Dave said:
Probably not the "wrong" way, just a different way, especially if you
write C code.

Oh, how poorly you know me! ;) I started learning C# a year ago, just
for fun, but that's about all I know (aside from HTML and CSS). I did
have a high school class in C++ a long, long time ago though.

Anyway, Python is my next venture, again just for fun. I guess my
problem was like you said, I was used to truncating toward zero, not
toward negative infinity. Knowing that that's how Python works fully
explains my problem now.
 

Ask a Question

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

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
474,284
Messages
2,571,411
Members
48,105
Latest member
KateDrozd

Latest Threads

Top