Reason for not allowing import twice but allowing reload()

Chris Angelico rosuav at gmail.com
Mon Feb 29 02:01:30 EST 2016


On Mon, Feb 29, 2016 at 5:40 PM,  <alien2utoo at gmail.com> wrote:
> We can not import a module twice in a session of Python (subsequent attempts to import same module don't result in any error though, but it is not-effective).
>
> However after making change to module, we can reload() it (if not reload(), we could possibly have reimport statement) to get the updates in module.
>
> I am a newbie in Python (learning via IDLE) and trying to understand
>
> - what is extra (special) that import does, that reload() doesn't?
> - if both do the same internally and externally, why subsequent imports of same module are ineffective?
> - if subsequent imports of same module in a session are not effective, why not simply flag those attempts as an error, rather than letting them go effect-less.
>
> Kindly help me understand the reasons behind.

Normally, you import a module because you want its features. For
instance, you can "import re" to get access to the Regular Expression
parser, or "import pandas" to load up the rather hefty third-party
numerical computation/analysis library of that name. Sometimes, this
can take a lot of work - importing pandas loads several hundred
modules in total, and can take a second or two, if it's not already in
the OS's disk cache. (Even if it is in cache, it takes a visible pause
- maybe 100-300 ms.) If two parts of your project need the same
module, it's way more efficient to make use of the already-loaded
module.

Additionally, sometimes it makes a lot of difference, and you _want_
to use the same module. When you "import sys", you absolutely must
access the same sys module that everyone else does; otherwise,
changing sys.stdout or sys.path wouldn't have any effect. And
depending on how it's implemented, sys.intern could create very subtle
bugs if you had two versions of it around.

So here's what happens (massively oversimplified) when you "import modulename":

1) Is modulename in sys.modules? If so, return that.
2) Step through sys.path, looking for the module. Can't find it? ImportError.
3) Run that program and create a module object. Put it into
sys.modules, and return it.

You can test that first step fairly easily:

>>> sys.modules["asdf"]="Haha"
>>> import asdf
>>> asdf
'Haha'

As a general rule, this is what you want (apart from sticking strings
into sys.modules, which is a VERY strange thing to do!). In fact, I
would recommend never using reload() unless you're absolutely sure of
what it does and how it's important. I've never used reload() in any
production code, ever. Ever.

The reason that repeating the import isn't flagged as an error is that
it's simply an assignment. If you write this code, Python won't warn
you:

>>> os = sys.modules["os"]
>>> os = sys.modules["os"]
>>> os = sys.modules["os"]
>>> os = sys.modules["os"]

Yet this is effectively what "import os" does. It's assignment, just
like any other assignment operation.

I believe it is theoretically possible to ask Python to give you a
warning (using an import hook), but generally, you should think about
imports simply as assignment.

ChrisA


More information about the Python-list mailing list