"from foo import *" is a really lazy programming practice that assumes there are no symbol clashes between the module's namespace and the current namespace.  It makes production code harder to maintain because the reader has to figure out whether a given function or class name is defined in the current namespace or merely mapped there from another module for convenience.

I know it is common in tutorials (especially C++ tutorials mapping 'std' into global) to make example code shorter and somehow easier to read (especially in books).  Unfortunately, the reason namespaces exist is rarely emphasized, which gives the impression that it is a common acceptable practice.  Everyplace I have worked has had the hard rule that modules are never mapped into the global namespace in production code (for both C++ and Python).

Restricting symbols in the global namespace to prevent clashes in module namespaces seems like backward reasoning to accommodate bad practices.  The fact that pylab takes care to allow mapping all of the numpy symbols into its namespace to make pylab a super namespace of the two has nothing to do with mapping the symbols into the global namespace.


On 9/4/20 3:30 PM, Todd wrote:
On Fri, Sep 4, 2020, 12:48 Cade Brown <brown.cade@gmail.com> wrote:
I am positing that Python should contain a constant (similar to True, False, None), called Infinity.

It would be equivalent to `float('inf')`, i.e. a floating point value representing a non-fininte value. It would be the positive constant; negative infinity could retrieved via `-Infinity`

Or, to keep float representation the same, the name `inf` could be used, but that does not fit Python's normal choice for such identifiers (but indeed, this is what C uses which is the desired behavior of string conversion)

I think there are a number of good reasons for this constant. For example:
  * It is also a fundamental constant (similar to True, False, and None), and should be representable as such in the language
  * Requiring a cast from float to string is messy, and also obviously less efficient (but this performance difference is likely insignificant)
      * Further, having a function call for something that should be a constant is a code-smell; in general str -> float conversion may throw an error or anything else and I'd rather not worry about that.
  * It would make the useful property that `eval(repr(x)) == x` for floating point numbers (currently, `NameError: name 'inf' is not defined`)

This makes it difficult to, for example, naively serialize a list of floats. For example:

>>> x = [1, 2, 3, 4]
>>> repr(x)
'[1, 2, 3, 4]'
>>> eval(repr(x)) == x
>>> x = [1, 2, 3, float('inf')]
>>> repr(x)
'[1, 2, 3, inf]'
>>> eval(repr(x)) == x
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<string>", line 1, in <module>
NameError: name 'inf' is not defined

To me, this is problematic; I would expect it to work seamlessly as it does with other floating point constants.

A few rebuttals/claims against:
  - Creating a new constant (Infinity) which is unassignable may break existing code

It will break an ENORMOUS amount of code.  Numpy has its own top-level "inf" variable.  So all code that uses "from numpy import *" will break.  Pylab imports numpy in that way, so "from pylab import *" will also break.  Whether you think this is a good approach or not, a ton of tutorials recommend doing this.  All of those tutorials will break in a way that is very hard to fix.

Python-ideas mailing list -- python-ideas@python.org
To unsubscribe send an email to python-ideas-leave@python.org
Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/GTPEHRE7VZCQD5CMCMGQ54XUBUQDUH6D/
Code of Conduct: http://python.org/psf/codeofconduct/

From there to here, from here to there,
funny things are everywhere.
           -- Theodore Geisel