Deprecate the round builtin
The builtin round function is completely useless. I've never seen anyone use it constructively. Usually people using it are new programmers who are not comfortable with or aware of string formatting. Sometimes people use it to poorly replicate functionality that's implemented correctly in the decimal module. Mike
On Wed, Sep 26, 2012 at 11:51 AM, Mike Graham <mikegraham@gmail.com> wrote:
The builtin round function is completely useless. I've never seen anyone use it constructively. Usually people using it are new programmers who are not comfortable with or aware of string formatting. Sometimes people use it to poorly replicate functionality that's implemented correctly in the decimal module.
You're probably right. It has ancient ancestry: it was one of the functions I copied directly from ABC. (It's actually more useful now that floats are printed with minimal digits.) But given the pain of removing a builtin, is it worth it? maybe we can just document the better ways of accomplishing its tasks? -- --Guido van Rossum (python.org/~guido)
On Wed, Sep 26, 2012 at 2:55 PM, Guido van Rossum <guido@python.org> wrote:
On Wed, Sep 26, 2012 at 11:51 AM, Mike Graham <mikegraham@gmail.com> wrote:
The builtin round function is completely useless. I've never seen anyone use it constructively. Usually people using it are new programmers who are not comfortable with or aware of string formatting. Sometimes people use it to poorly replicate functionality that's implemented correctly in the decimal module.
You're probably right. It has ancient ancestry: it was one of the functions I copied directly from ABC. (It's actually more useful now that floats are printed with minimal digits.)
But given the pain of removing a builtin, is it worth it? maybe we can just document the better ways of accomplishing its tasks?
I think it is reasonable with the right justifications, deprecation period, and obvious migration path. Also, I'd be completely in support of dropping round() and agree it gets misused and leads to too much confusion. We should promote the right ways, and some times to show the right path you need to lock another door and throw away the key.
-- --Guido van Rossum (python.org/~guido) _______________________________________________ Python-ideas mailing list Python-ideas@python.org http://mail.python.org/mailman/listinfo/python-ideas
-- Read my blog! I depend on your acceptance of my opinion! I am interesting! http://techblog.ironfroggy.com/ Follow me if you're into that sort of thing: http://www.twitter.com/ironfroggy
On 27/09/12 11:14, Calvin Spealman wrote:
On Wed, Sep 26, 2012 at 2:55 PM, Guido van Rossum<guido@python.org> wrote:
On Wed, Sep 26, 2012 at 11:51 AM, Mike Graham<mikegraham@gmail.com> wrote:
The builtin round function is completely useless. I've never seen anyone use it constructively. Usually people using it are new programmers who are not comfortable with or aware of string formatting. Sometimes people use it to poorly replicate functionality that's implemented correctly in the decimal module.
You're probably right. It has ancient ancestry: it was one of the functions I copied directly from ABC. (It's actually more useful now that floats are printed with minimal digits.)
But given the pain of removing a builtin, is it worth it? maybe we can just document the better ways of accomplishing its tasks?
I think it is reasonable with the right justifications, deprecation period, and obvious migration path.
Also, I'd be completely in support of dropping round() and agree it gets misused and leads to too much confusion. We should promote the right ways, and some times to show the right path you need to lock another door and throw away the key.
I don't believe that round gets misused and causes confusion to any significant degree. That belief is based on many years experience on two high-traffic mailing lists with many beginners. I've seen plenty of examples of beginners confused that Python can't add floats correctly, but if I've ever seen somebody confused by round, it was so uncommon and so long ago I've forgotten it. It seems to me that this proposal is based on a purely theoretical fear that some people manage to escape being confused by the far more obvious floating point gotchas[1] but can't understand round. There are much more common, and bigger, surprises with binary floats than round, and it seems to me that depreciating it just disrupts those who do use it for no real benefit. So -1 on such a change. I could be convinced to change that to a -0.5 if round were moved to the math module exactly as is, including the second argument. But even that is a disruption for no meaningful benefit. [1] I managed to surprise myself the other week when I "discovered" what was obvious in hindsight, that for sufficiently large values all finite floats are even integer values. I had known the "integer value" part, but was surprised by the "even" part. I shouldn't have been. -- Steven
On Wed, Sep 26, 2012 at 10:15 PM, Steven D'Aprano <steve@pearwood.info> wrote:
I don't believe that round gets misused and causes confusion to any significant degree. That belief is based on many years experience on two high-traffic mailing lists with many beginners. I've seen plenty of examples of beginners confused that Python can't add floats correctly, but if I've ever seen somebody confused by round, it was so uncommon and so long ago I've forgotten it.
It seems to me that this proposal is based on a purely theoretical fear that some people manage to escape being confused by the far more obvious floating point gotchas[1] but can't understand round. There are much more common, and bigger, surprises with binary floats than round, and it seems to me that depreciating it just disrupts those who do use it for no real benefit.
I don't have a "purely theoretical fear" regarding round; I simply have had a different experience and analysis than you. I have long been an active member of the official Python IRC channel and other Python IRC channels and of various other support communities (I beat StackOverflow before they added the new levels :) ). I have seen many, many people have questions about round and they almost always don't want to be using it. Most often, people really want to be using string formatting, but there are all sorts of . I posted here today after yet another person came into #python with a round question where they didn't want round. My problem with round isn't that new people don't understand it--it's that there's nothing worth understanding. (With floats, the situation merely requires education then people can use floats well. With round, when you learn you stop using it.) round(x, n) for n>0 is quite simply not sane code. rounding is an exact operation and it does not make any sense to do base 10 rounding on base 2 numbers in this way. round for n <= 0 is not so criminal, but it sometimes-inconveniently returns a float and it's trivially written shorter/as-easily for n=0 and seldom actually needed for n<0. Mike
Mike Graham wrote:
round(x, n) for n>0 is quite simply not sane code.
I've occasionally used round(x,n) with n>0 - as a quick way to normalize away numeric imprecisions and have values generated by a computation recognized as identical set elements or dictionary keys. I'd have used a function to round in binary instead of decimal had one been handy, but otoh I don't see it would make a real difference, would it?
On Wed, Sep 26, 2012 at 7:51 PM, Mike Graham <mikegraham@gmail.com> wrote:
The builtin round function is completely useless. I've never seen anyone use it constructively
I disagree that it's *completely* useless: the one-argument form (take a float, return the closest integer) is a fundamental and useful mathematics operation, just like floor and ceiling. It would be crazy to get rid of that. I could live with it moving from builtins into the math module, though. Agreed that the two-argument form causes a lot of confusion, though. -- Mark
Mark Dickinson wrote:
On Wed, Sep 26, 2012 at 7:51 PM, Mike Graham <mikegraham@gmail.com> wrote:
The builtin round function is completely useless. I've never seen anyone use it constructively
I disagree that it's *completely* useless: the one-argument form (take a float, return the closest integer) is a fundamental and useful mathematics operation, just like floor and ceiling. It would be crazy to get rid of that. I could live with it moving from builtins into the math module, though.
Agreed that the two-argument form causes a lot of confusion, though.
It's actually quite common in finance and time calculations to round to the nearest say basis point, cent or say micro second in calculations (rather than just string formatting). round() is perfect for that and easy to use. -- Marc-Andre Lemburg eGenix.com Professional Python Services directly from the Source (#1, Sep 26 2012)
Python/Zope Consulting and Support ... http://www.egenix.com/ mxODBC.Zope.Database.Adapter ... http://zope.egenix.com/ mxODBC, mxDateTime, mxTextTools ... http://python.egenix.com/
2012-10-29: PyCon DE 2012, Leipzig, Germany ... 33 days to go 2012-10-23: Python Meeting Duesseldorf ... 27 days to go 2012-09-26: Released mxODBC.Connect 2.0.1 ... http://egenix.com/go34 2012-09-25: Released mxODBC 3.2.1 ... http://egenix.com/go33 eGenix.com Software, Skills and Services GmbH Pastor-Loeh-Str.48 D-40764 Langenfeld, Germany. CEO Dipl.-Math. Marc-Andre Lemburg Registered at Amtsgericht Duesseldorf: HRB 46611 http://www.egenix.com/company/contact/
On 26 September 2012 20:36, M.-A. Lemburg <mal@egenix.com> wrote:
Mark Dickinson wrote:
On Wed, Sep 26, 2012 at 7:51 PM, Mike Graham <mikegraham@gmail.com> wrote:
The builtin round function is completely useless. I've never seen anyone use it constructively
I disagree that it's *completely* useless: the one-argument form (take a float, return the closest integer) is a fundamental and useful mathematics operation, just like floor and ceiling. It would be crazy to get rid of that. I could live with it moving from builtins into the math module, though.
Agreed that the two-argument form causes a lot of confusion, though.
It's actually quite common in finance and time calculations to round to the nearest say basis point, cent or say micro second in calculations (rather than just string formatting). round() is perfect for that and easy to use.
Agreed. I've rounded before. It's useful. Maybe not as useful as all() or whatever, but I don't see how it's "redundant".
On Wed, Sep 26, 2012 at 8:36 PM, M.-A. Lemburg <mal@egenix.com> wrote:
It's actually quite common in finance and time calculations to round to the nearest say basis point, cent or say micro second in calculations
That's exactly where the problems creep in, though. Naive users expect rounding to give 'correct' results for decimal halfway cases, and then are surprised when it doesn't.
round(2.675, 2) 2.67
So you end up explaining again and again that computing binary approximations to decimal rounds of binary approximations of decimal halfway cases is a bad idea. Mark
Mark Dickinson wrote:
On Wed, Sep 26, 2012 at 8:36 PM, M.-A. Lemburg <mal@egenix.com> wrote:
It's actually quite common in finance and time calculations to round to the nearest say basis point, cent or say micro second in calculations
That's exactly where the problems creep in, though. Naive users expect rounding to give 'correct' results for decimal halfway cases, and then are surprised when it doesn't.
round(2.675, 2) 2.67
So you end up explaining again and again that computing binary approximations to decimal rounds of binary approximations of decimal halfway cases is a bad idea.
But that's the fault of round(), is it ? ;-) It's more one of educating people of what to expect when working with floats. Your example is a typical case that comes up when people enter examples and wonder why they don't see the expected results. In calculations, statistics, numeric, etc. such corner cases are not all that common, so things are not as bad as they may appear on first sight. -- Marc-Andre Lemburg eGenix.com Professional Python Services directly from the Source (#1, Sep 26 2012)
Python/Zope Consulting and Support ... http://www.egenix.com/ mxODBC.Zope.Database.Adapter ... http://zope.egenix.com/ mxODBC, mxDateTime, mxTextTools ... http://python.egenix.com/
2012-10-29: PyCon DE 2012, Leipzig, Germany ... 33 days to go 2012-10-23: Python Meeting Duesseldorf ... 27 days to go 2012-09-26: Released mxODBC.Connect 2.0.1 ... http://egenix.com/go34 2012-09-25: Released mxODBC 3.2.1 ... http://egenix.com/go33 eGenix.com Software, Skills and Services GmbH Pastor-Loeh-Str.48 D-40764 Langenfeld, Germany. CEO Dipl.-Math. Marc-Andre Lemburg Registered at Amtsgericht Duesseldorf: HRB 46611 http://www.egenix.com/company/contact/
M.-A. Lemburg wrote:
In calculations, statistics, numeric, etc. such corner cases are not all that common, so things are not as bad as they may appear on first sight.
If the corner cases don't matter, I'd say you don't need to round your internal representations in the first place. Rounding on output is sufficient and probably preferable. If they *do* matter -- such as when cents need to add up exactly -- you're much better off using Decimals. Two-argument round() is an attractive nuisance in that case, IMO. -- Greg
2012/9/26 M.-A. Lemburg <mal@egenix.com>:
round(2.675, 2) 2.67
So you end up explaining again and again that computing binary approximations to decimal rounds of binary approximations of decimal halfway cases is a bad idea.
But that's the fault of round(), is it ? ;-) It's more one of educating people of what to expect when working with floats.
Could we change the round() behavior? The second parameter is the number of decimal places, so the operation could be defined in terms of decimal digits. A similar change was already done for float.__str__. -- Amaury Forgeot d'Arc
On 2012-09-26 21:17, M.-A. Lemburg wrote:
Mark Dickinson wrote:
On Wed, Sep 26, 2012 at 8:36 PM, M.-A. Lemburg <mal@egenix.com> wrote:
It's actually quite common in finance and time calculations to round to the nearest say basis point, cent or say micro second in calculations
That's exactly where the problems creep in, though. Naive users expect rounding to give 'correct' results for decimal halfway cases, and then are surprised when it doesn't.
round(2.675, 2) 2.67
So you end up explaining again and again that computing binary approximations to decimal rounds of binary approximations of decimal halfway cases is a bad idea.
But that's the fault of round(), is it ? ;-) It's more one of educating people of what to expect when working with floats.
Your example is a typical case that comes up when people enter examples and wonder why they don't see the expected results.
In calculations, statistics, numeric, etc. such corner cases are not all that common, so things are not as bad as they may appear on first sight.
If we're going to move 'round' into 'math' because it sometimes gives results which puzzle naive users, shouldn't we do the same to 'float'? :-)
On 27/09/12 10:32, Bill Janssen wrote:
MRAB<python@mrabarnett.plus.com> wrote:
If we're going to move 'round' into 'math' because it sometimes gives results which puzzle naive users, shouldn't we do the same to 'float'? :-)
Ah, but float is a type, not a function.
What difference does that make? Floats sometimes give results which puzzle naive users. py> L = [1/10]*10 py> print(L) [0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1] py> sum(L) # should be 1.0 0.9999999999999999 "Why doesn't Python add up correctly?" And so we have to explain that the float 0.1 is not actually 0.1 because you can't represent 0.1 as a finite binary fraction, due to some fairly subtle mathematics that goes right past most people. The float 0.1 is actually a tiny bit *larger* than the decimal 0.1, but when you add ten of them together, you end up with a number that it a tiny bit *smaller* than the expected result. Don't you just love binary floating point? Matthew used a smiley there, but I think there is a very strong case for making the default floating point numeric type Decimal rather than float. Decimals behave more like people expect, and they interact better with other numeric types (ints and Fractions) than floats. Obviously this will be a big change, almost certainly requiring a PEP and a long lead time, e.g. Decimal could become a built-in in Python 3.4, then in 3.5 you could do "from __future__ import decimal_floats", and in 3.6 it could be the standard behaviour, or perhaps a runtime flag to switch between binary and decimal floats. I hate to think how much work would be involved. -- Steven
On 2012-09-27 01:32, Bill Janssen wrote:
MRAB <python@mrabarnett.plus.com> wrote:
If we're going to move 'round' into 'math' because it sometimes gives results which puzzle naive users, shouldn't we do the same to 'float'? :-)
Ah, but float is a type, not a function.
They are both (first-class) objects, aren't they? Why treat them differently? Surely such discrimination is unPythonic? :-)
"M.-A. Lemburg" <mal@egenix.com> writes:
Mark Dickinson wrote:
round(2.675, 2) 2.67
So you end up explaining again and again that computing binary approximations to decimal rounds of binary approximations of decimal halfway cases is a bad idea.
But that's the fault of round(), is it ? ;-) It's more one of educating people of what to expect when working with floats.
It's the fault of the two-parameter ‘round’, yes. It is an attractive nuisance that appears to promise one thing but doesn't deliver, and makes it easy to do the wrong thing by mistake. Where feasible, and where it doesn't unreasonably restrict functionality, IMO Python should make it difficult to do the wrong thing by mistake.
Your example is a typical case that comes up when people enter examples and wonder why they don't see the expected results.
I think this is an argument that deprecating, and eventually removing, the two-parameter form of ‘round’, would be helpful overall. -- \ “Consider the daffodil. And while you're doing that, I'll be | `\ over here, looking through your stuff.” —Jack Handey | _o__) | Ben Finney
On 27/09/12 06:02, Mark Dickinson wrote:
On Wed, Sep 26, 2012 at 8:36 PM, M.-A. Lemburg<mal@egenix.com> wrote:
It's actually quite common in finance and time calculations to round to the nearest say basis point, cent or say micro second in calculations
That's exactly where the problems creep in, though. Naive users expect rounding to give 'correct' results for decimal halfway cases, and then are surprised when it doesn't.
round(2.675, 2) 2.67
So you end up explaining again and again that computing binary approximations to decimal rounds of binary approximations of decimal halfway cases is a bad idea.
Pretty much *everything* about binary floats is surprising to people who expect decimal semantics. Unless we're going to make Decimal the default floating point type, and shift binary floats to a module, I don't see any way around that, and a particularly don't see any reason to single round() out as more confusing than any of the other float gotchas. Speaking from my experience on the tutor@ and python-list@python.org mailing lists, I believe that problems with round are vanishingly rare, probably an order of magnitude fewer than "why doesn't Python add my two floats correctly?" type questions. -- Steven
On Sep 26, 2012, at 7:07 PM, Steven D'Aprano <steve@pearwood.info> wrote:
Pretty much *everything* about binary floats is surprising to people who expect decimal semantics. Unless we're going to make Decimal the default floating point type, and shift binary floats to a module, I don't see any way around that, and a particularly don't see any reason to single round() out as more confusing than any of the other float gotchas.
Speaking from my experience on the tutor@ and python-list@python.org mailing lists, I believe that problems with round are vanishingly rare, probably an order of magnitude fewer than "why doesn't Python add my two floats correctly?" type questions.
My experience teaching and consulting is matches your experience on tutor. I agree with your suggestion to leave round() untouched. Raymond
On Wed, Sep 26, 2012 at 3:36 PM, M.-A. Lemburg <mal@egenix.com> wrote:
It's actually quite common in finance and time calculations to round to the nearest say basis point, cent or say micro second in calculations (rather than just string formatting). round() is perfect for that and easy to use.
Rounding to the nearest cent is an important operation, but it's not one that round really handles well. It certainly can't always round you exactly to the nearest hundredth--it can round you there with some inaccuracy when you're doing it to have an exact number. We have the decimal module (or sometimes just plain int) to handle this in a much more robust, correct way. I'm not personally familiar with the cases where one would want to round time like that for computations, but I can't help but suspect that if you want a quantity in a number of microseconds, you'd be wanting it to be exact as well. round only appears to be useful. Using it to try to get something "in cents" or similar is a strong code smell and probably a bug. Mike
On Wed, Sep 26, 2012 at 3:36 PM, M.-A. Lemburg <mal@egenix.com> wrote:
It's actually quite common in finance and time calculations to round to the nearest say basis point, cent or say micro second in calculations (rather than just string formatting). round() is perfect for that and easy to use.
On the other hand, having round with a second parameter to return a Decimal would be quite usefull. I can't see a way of changing the type returned by the built-in round without crashing half the World --- but maybe it would be possible to deprecate only the two-parameter form of the built-in round, and add a decimal.round Decimal factory? js -><-
On the other hand, having round with a second parameter to return a Decimal would be quite usefull. I can't see a way of changing the type returned by the built-in round without crashing half the World --- but maybe it would be possible to deprecate only the two-parameter form of the built-in round, and add a decimal.round Decimal factory?
On second thought, the idea of "namespaces" within the interpreter (like Tim Peters was suggesting I think in the doctest module) could put some order to built-ins and globals within the interpreter. round(), hex() and others could be in the namespace "Numbers" (Named by their associated type), similarly for the other type-specific builtins. Create a keyword "expose" to dump a particular namespace into the global scope when you don't want to type "Numbers.round(f)". Thoughts? markj
On Wed, Sep 26, 2012 at 04:15:52PM -0500, Mark Adam <dreamingforward@gmail.com> wrote:
On second thought, the idea of "namespaces" within the interpreter (like Tim Peters was suggesting I think in the doctest module) could put some order to built-ins and globals within the interpreter. round(), hex() and others could be in the namespace "Numbers" (Named by their associated type), similarly for the other type-specific builtins.
Create a keyword "expose" to dump a particular namespace into the global scope when you don't want to type "Numbers.round(f)".
What is the difference between such namespaces and modules (which *are* namespaces)? Oleg. -- Oleg Broytman http://phdru.name/ phd@phdru.name Programmers don't die, they just GOSUB without RETURN.
On Wed, Sep 26, 2012 at 4:21 PM, Oleg Broytman <phd@phdru.name> wrote:
On Wed, Sep 26, 2012 at 04:15:52PM -0500, Mark Adam <dreamingforward@gmail.com> wrote:
On second thought, the idea of "namespaces" within the interpreter (like Tim Peters was suggesting I think in the doctest module) could put some order to built-ins and globals within the interpreter. round(), hex() and others could be in the namespace "Numbers" (Named by their associated type), similarly for the other type-specific builtins.
Create a keyword "expose" to dump a particular namespace into the global scope when you don't want to type "Numbers.round(f)".
What is the difference between such namespaces and modules (which *are* namespaces)?
Modules reside on file and are changeable, Namespaces solely in memory, defined by the Interpreter itself. mark
On Wed, Sep 26, 2012 at 04:30:33PM -0500, Mark Adam <dreamingforward@gmail.com> wrote:
On Wed, Sep 26, 2012 at 4:21 PM, Oleg Broytman <phd@phdru.name> wrote:
On Wed, Sep 26, 2012 at 04:15:52PM -0500, Mark Adam <dreamingforward@gmail.com> wrote:
On second thought, the idea of "namespaces" within the interpreter (like Tim Peters was suggesting I think in the doctest module) could put some order to built-ins and globals within the interpreter. round(), hex() and others could be in the namespace "Numbers" (Named by their associated type), similarly for the other type-specific builtins.
Create a keyword "expose" to dump a particular namespace into the global scope when you don't want to type "Numbers.round(f)".
What is the difference between such namespaces and modules (which *are* namespaces)?
Modules reside on file and are changeable,
Oh, really? What is the file for module sys? thread? zipimport?
Namespaces solely in memory, defined by the Interpreter itself.
Oleg. -- Oleg Broytman http://phdru.name/ phd@phdru.name Programmers don't die, they just GOSUB without RETURN.
Mark Adam wrote:
Modules reside on file and are changeable, Namespaces solely in memory, defined by the Interpreter itself.
Presumably they would be implemented as module objects, created automatically at interpreter startup instead of being loaded from a file. In which case "built-in module" might be a better term for them. And their names should start with lower case. Also you wouldn't need new syntax to get names out of them, just the existing import machinery: from numbers import * -- Greg
Why suggest adding new round-like functions to the math module rather than defining a new round method on all numerical objects? -gps
On 30 September 2012 22:38, Gregory P. Smith <greg@krypto.org> wrote:
Why suggest adding new round-like functions to the math module rather than defining a new round method on all numerical objects?
round("") Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: type str doesn't define __round__ method
It seems it is done like that already ;) This seems like a problem for the proposal, though: we can't have it in the math library if it's a method!
On Sun, Sep 30, 2012 at 2:51 PM, Joshua Landau <joshua.landau.ws@gmail.com> wrote:
On 30 September 2012 22:48, Joshua Landau <joshua.landau.ws@gmail.com> wrote:
This seems like a problem for the proposal, though: we can't have it in the math library if it's a method!
Now I think about it: yeah, it can be. We just coerce to float/decimal first. *sigh* math.ceil(x), math.floor(x), and math.trunc(x) and round(x) already call the special methods x.__ceil__, x.__floor__, x.__round__, and x.__trunc__. So those four functions already work with decimal instances (and other numeric types that support those methods.)
casevh
_______________________________________________ Python-ideas mailing list Python-ideas@python.org http://mail.python.org/mailman/listinfo/python-ideas
On 30 September 2012 23:08, Case Van Horsen <casevh@gmail.com> wrote:
On Sun, Sep 30, 2012 at 2:51 PM, Joshua Landau <joshua.landau.ws@gmail.com> wrote:
On 30 September 2012 22:48, Joshua Landau <joshua.landau.ws@gmail.com> wrote:
This seems like a problem for the proposal, though: we can't have it in the math library if it's a method!
Now I think about it: yeah, it can be. We just coerce to float/decimal first. *sigh* math.ceil(x), math.floor(x), and math.trunc(x) and round(x) already call the special methods x.__ceil__, x.__floor__, x.__round__, and x.__trunc__. So those four functions already work with decimal instances (and other numeric types that support those methods.)
math.ceil("") Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: *a float is required*
How deceptive... I hope you forgive me for not realizing that (even though I must have seen the __ceil__ and __floor__ methods a thousand times). OK, carry on.
On 9/30/2012 6:19 PM, Joshua Landau wrote:
>>> math.ceil("") Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: *a float is required*
How deceptive... I hope you forgive me for not realizing that (even though I must have seen the __ceil__ and __floor__ methods a thousand times). OK, carry on.
The obsolete error message should be fixed. A number is required. Or perhaps 'float or number with __ceil__ method'. -- Terry Jan Reedy
On Sun, Sep 30, 2012 at 02:38:33PM -0700, Gregory P. Smith wrote:
Why suggest adding new round-like functions to the math module rather than defining a new round method on all numerical objects?
round already calls the special __round__ method, and in 3.2 works with ints, floats, Decimals and Fractions. Only complex misses out. py> round(12345, -2) 12300 py> from decimal import Decimal as D py> round(D("1.2345"), 2) Decimal('1.23') py> from fractions import Fraction as F py> round(F(12345, 10000), 2) Fraction(123, 100) -- Steven
On Thu, Sep 27, 2012 at 5:23 AM, Greg Ewing <greg.ewing@canterbury.ac.nz> wrote:
Presumably they would be implemented as module objects, created automatically at interpreter startup instead of being loaded from a file.
In which case "built-in module" might be a better term for them. And their names should start with lower case.
That's cool. YES, lowercase.
Also you wouldn't need new syntax to get names out of them, just the existing import machinery:
from numbers import *
Well, to me there must be a clear partitioning. The stuff in the builtin [module] sets the tone for the whole interpreter environment (and I think python culture itself). If one were to use the standard import language (like in your example), it confuses one "semantically" -- because you're suggesting to treat a it (i.e. a whole class of "things") as something optional. Does that make sense? Thanks, markj
On Sun, Sep 30, 2012 at 11:46:05PM -0500, Mark Adam wrote:
On Thu, Sep 27, 2012 at 5:23 AM, Greg Ewing <greg.ewing@canterbury.ac.nz> wrote:
Presumably they would be implemented as module objects, created automatically at interpreter startup instead of being loaded from a file.
In which case "built-in module" might be a better term for them. And their names should start with lower case.
That's cool. YES, lowercase.
I'm not sure why "built-in module" is a better term for something which I gather is a separate namespace within a module, so you can have: module.spam # global namespace module.sub.spam # sub is a "submodule" or "namespace" but sub has no independent existence as a file on disk. If that's what we're discussing, I don't think that "built-in module" is a good name, since it isn't *built-in*. We already have something called "built-in modules" -- modules like sys which actually are built-in to the Python virtual machine.
Also you wouldn't need new syntax to get names out of them, just the existing import machinery:
from numbers import *
Well, to me there must be a clear partitioning.
The stuff in the builtin [module] sets the tone for the whole interpreter environment (and I think python culture itself). If one were to use the standard import language (like in your example), it confuses one "semantically" -- because you're suggesting to treat a it (i.e. a whole class of "things") as something optional.
Does that make sense?
Not to me, I'm afraid. -- Steven
On Mon, Oct 1, 2012 at 1:05 AM, Steven D'Aprano <steve@pearwood.info> wrote:
I'm not sure why "built-in module" is a better term for something which I gather is a separate namespace within a module, so you can have:
Yeah, I'm not really sure it makes sense to call it a module at all. I was sort of capitulating about the use of the word "module". It's not like you can do "import __builtins__" in the interpreter, so if one is going to call it a module (like the interpreter currently does), one should see that it is a very special exception of the word. I prefer "namespace", it's the built-in namespace which is a synonym for "the global module".
Well, to me there must be a clear partitioning.
The stuff in the builtin [module] sets the tone for the whole interpreter environment (and I think python culture itself). If one were to use the standard import language (like in your example), it confuses one "semantically" -- because you're suggesting to treat a it (i.e. a whole class of "things") as something optional.
Does that make sense?
Not to me, I'm afraid.
Hopefully the above makes it a little clearer. But, it's as if you're going on a road trip, you want to travel efficient and light -- what you include in your backpack ("interpreter environment") is your "builtin" and everything else you'll "buy"/import on the road. Modules are those things on the road. mark
On Mon, Oct 1, 2012 at 9:42 PM, Mark Adam <dreamingforward@gmail.com> wrote:
On Mon, Oct 1, 2012 at 1:05 AM, Steven D'Aprano <steve@pearwood.info> wrote:
I'm not sure why "built-in module" is a better term for something which I gather is a separate namespace within a module, so you can have:
Yeah, I'm not really sure it makes sense to call it a module at all. I was sort of capitulating about the use of the word "module". It's not like you can do "import __builtins__" in the interpreter, so if one is going to call it a module (like the interpreter currently does), one should see that it is a very special exception of the word.
"import __builtin__" in Python 2, "import builtins" in Python 3. The contents of those modules are implicitly made available to all Python code running in that process. Cheers, Nick. -- Nick Coghlan | ncoghlan@gmail.com | Brisbane, Australia
Mark Adam wrote:
It's not like you can do "import __builtins__" in the interpreter,
But you *can* do "import __builtin__". Also, "sys" is created at interpreter startup and doesn't correspond to any disk file, but we don't seem to mind calling it a module and using the same import syntax to access it. The only difference I can see with these proposed namespace things is that they would be pre-bound to names in the builtin namespace.
But, it's as if you're going on a road trip, you want to travel efficient and light -- what you include in your backpack ("interpreter environment") is your "builtin" and everything else you'll "buy"/import on the road. Modules are those things on the road.
The sys module violates this taxonomy -- it's already in your backpack, just tucked away in a paper bag that you need to open first. -- Greg
Normally deprecation means you keep it forever but don't mention it much in the docs... On Sep 26, 2012 5:16 PM, "Mark Adam" <dreamingforward@gmail.com> wrote:
On the other hand, having round with a second parameter to return a Decimal would be quite usefull. I can't see a way of changing the type returned by the built-in round without crashing half the World --- but maybe it would be possible to deprecate only the two-parameter form of the built-in round, and add a decimal.round Decimal factory?
On second thought, the idea of "namespaces" within the interpreter (like Tim Peters was suggesting I think in the doctest module) could put some order to built-ins and globals within the interpreter. round(), hex() and others could be in the namespace "Numbers" (Named by their associated type), similarly for the other type-specific builtins.
Create a keyword "expose" to dump a particular namespace into the global scope when you don't want to type "Numbers.round(f)".
Thoughts?
markj _______________________________________________ Python-ideas mailing list Python-ideas@python.org http://mail.python.org/mailman/listinfo/python-ideas
On Wed, 26 Sep 2012 17:21:40 -0400 Daniel Holth <dholth@gmail.com> wrote:
Normally deprecation means you keep it forever but don't mention it much in the docs...
Not really. Most deprecated things disappear one or two versions after they are deprecated. We only keep something forever when removing it would break a lot of code and keeping it is cheap. Regards Antoine. -- Software development and contracting: http://pro.pitrou.net
participants (24)
-
Alexander Belopolsky
-
Amaury Forgeot d'Arc
-
Antoine Pitrou
-
Ben Finney
-
Bill Janssen
-
Boris Borcic
-
Calvin Spealman
-
Case Van Horsen
-
Daniel Holth
-
Greg Ewing
-
Gregory P. Smith
-
Guido van Rossum
-
Joao S. O. Bueno
-
Joshua Landau
-
M.-A. Lemburg
-
Mark Adam
-
Mark Dickinson
-
Mike Graham
-
MRAB
-
Nick Coghlan
-
Oleg Broytman
-
Raymond Hettinger
-
Steven D'Aprano
-
Terry Reedy