tags:

views:

126

answers:

3

Hi all,

I've run into some behavior from Python 2.6.1 that I didn't expect. Here is some trivial code to reproduce the problem:

---- ControlPointValue.py ------
class ControlPointValue:
   def __init__(self):
      pass

---- ControlPointValueSet.py ----
import ControlPointValue

---- main.py --------------------
from ControlPointValue import *
from ControlPointValueSet import *

val = ControlPointValue()

.... here is the error I get when I run main.py (under OS/X Snow Leopard, if it matters):

jeremy-friesners-mac-pro-3:~ jaf$ python main.py 
Traceback (most recent call last):
  File "main.py", line 4, in <module>
    val = ControlPointValue()
TypeError: 'module' object is not callable

Can someone explain what is going on here? Is Python getting confused because the class name is the same as the file name? If so, what is the best way to fix the problem? (I'd prefer to have my python files named after the classes that are defined in them)

Thanks, Jeremy

A: 

I believe the conventional answer is: don't use 'from foo import *', use 'import foo'

dlowe
Yes, that does fix the problem... I'm hoping to gain some insight as to why the posted code doesn't work, however.
Jeremy Friesner
+8  A: 

I don't think it's unexpected. What you are basically doing is:

1) the first import in main.py imports the contents of ControlPointValue module into the global namespace. this produces a class bound to that name.

2) the second import in main.py imports the contents of ControlPointValueSet module into the global namespace. This module imports ControlPointValue module. This overwrites the binding in the global namespace, replacing the binding for that name from the class to the module.

To solve, I would suggest you not to import *, ever. Always keep the last module prefix. For example, if you have foo/bar/baz/bruf.py containing a class Frobniz, do

from foo.bar.baz import bruf

and then use bruf.Frobniz()

Stefano Borini
It was unexpected to me... :) Thanks for the explanation, that makes sense.
Jeremy Friesner
I mean, it's not a bug. It's a feature.
Stefano Borini
Yes. However, "import *" is sometimes reasonable: doing "from math import *" does make sense, for instance, when you have lots of formulas.
EOL
+3  A: 

In addition to the other suggestions about star imports, don't name your module and your class the same. Follow pep8's suggestions and give your modules short all lower case names and name your classes LikeThis. E.g.

---- controlpoints.py ------
class ControlPointValue:
   def __init__(self):
      pass

---- valuesets.py ----
from controlpoints import ControlPointValue

---- main.py --------------------
from controlpoints import ControlPointValue
from valuesets import *

val = ControlPointValue()
whaley