Future division patch available (PEP 238)

David Boddie david at boddie.net
Wed Jul 25 13:01:24 EDT 2001


tanzer at swing.co.at (Christian Tanzer) wrote in message news:<mailman.996052189.14819.python-list at python.org>...
> Guido,
> 
> I deeply respect your language design skills and I appreciate your
> ongoing improvements. I'm impatiently looking forward to using many of
> the features new in 2.2.

I'd like to echo these sentiments. One of the things I like about
Python is its pragmatism. For example: although it provides classes
and objects, it is forgiving to those of us who were raised without
them.

[Problems associated with backwards compatibility snipped.]

>   What if `/` applied to two integer values returned neither an
>   integer nor a float but an object carrying the float result but
>   behaving like an integer if used in an integer context?
> 
>   For instance:
> 
>       >>> x = 1/2
>       >>> type(x)
>       <type 'Ratio'>
>       >>> print "%d %f %s" % (x, x, x)
>       0 0.5 0.5
>       >>> 2 * x
>       0
>       >>> 2. * x
>       1.0
> 
>    The difficult issue here is how `integer context` is defined.
>    Should multiplication by an integer be considered an integer
>    context? Pro: would preserve correctness of existing code like
>    `(size / 8) * 8`. Con: is incompatible with Rationals which might
>    be added in the future.

A problem arises if the type of the result (x in this example) is not
immediately resolved, requiring this context to be carried forward. A
"neutral" operation immediately following the assignment above, such
as a print statement (for want of a better example) or even another
division would further complicate the issue by leaving the
interpretation of the result until later when the original context is
unavailable.

[...]

> - If there is a possibility of specifying division semantics on a
>   per module case (via a directive or the file extension), it should
>   also be possible to specify the semantics for thingies like
>   `compile`, `execfile`, `exec`, and `eval`.
> 
>   This only works if absence of a semantics indicator means old-style
>   division. 

This has to be the best way to go. A substantial change to the
behaviour of the language should require the module author's explicit
intent.

>   I think this would go the farthest to alleviate compatibility
>   problems. I understand your desire to avoid dragging the past around
>   with you wherever you go and I like Python for its cleanliness. But
>   in this case, it might be worthwhile to carry the ballast.

If the behaviour of the / operator can be assigned on a per module
basis, and it is made explicit where changes to the default behaviour
occur, then what is the harm of carrying the old (standard) behaviour
forward?

Without wanting to detract from Christian's points above, I'd like to
make a few observations. I apologise in advance if you've read these
too many times already:

I migrated to Python from RLaB (a Matlab-like language) and was
surprised by the behaviour of integer division. However, reading the
tutorial made it clear that the / operator performed "integer
division" and that the % operator gave the modulus(?) of the result.
Since this is the main (most convenient) way to perform integer
division on current versions of Python, one would expect that to
change the behaviour of / would be to break most code which previously
performed integer division.

Introducing // for int/int -> *float* (as has been suggested as a
counter-measure to // for int/int -> int) isn't going to help since it
will either be a special case operator, or it will have to be extended
to work with float/float and mixed type operations. Otherwise
programmers will have to explicitly check for two integer arguments
and apply a different operator in that case.

I expect that under other circumstances there would be an outcry over
introducing // at all, as it going against the general preference for
readability in Python.

In my opinion, PEP 238 is something of a half measure. It takes away /
for integer division yet doesn't introduce the "div" keyword (or the
"mod" keyword for that matter). However, if it did include these then
I suspect that it would attract even more criticism.

Since one outcome of the PEP is to have int/int -> rational, then
shouldn't we wait until rationals have become standard issue, or have
they already? Otherwise we'll have to go through this all over again,
and nobody wants that.



One solution to the problem that / doesn't do what is expected, at
least during interactive mode, is to retain the standard behaviour by
default with the option to change this on a per module basis. However,
in interactive mode, the default would be to have the new division
behaviour switched *on* with a suitable warning reminding the user
that this is the case. Therefore, nobody is surprised at the command
line, and old modules continue to work as normal.

Although I expect that there creatures that are immune to this
particular magic bullet. <wink>

pragmatism-always-wins-ly y'rs - David



More information about the Python-list mailing list