问题
I'm cleaning up a project that was refactored into smaller .py files. I noticed that a lot of modules are being imported again and again in various files. Some statements are in files that import another which has the same import statement used by the importing file. For example:
main.py
import alt
print (os.getcwd())
alt.py
import os
The print(os.getcwd())
throws a NameError: name 'os' is not defined
. Shouldn't os
be part of sys.modules
when the import statement is executed in alt.py?
Is it possible to use a module imported by another module that was imported first?
回答1:
They are available in the following namespace:
import alt
print (alt.os.getcwd())
回答2:
To answer your immediate question, it is possible but not recommended.
Imports adjust the namespace in which they are made. This means that alt
has an attribute os
that can be accessed in main
as
print(alt.os.getcwd())
This is not the recommended way, however, since it makes it less clear which actual os
module you are using. You should do import os
directly in main
. This will not create a separate module object, so do not worry about cluttering your memory with duplicate modules.
The first time an import is encountered during runtime, it is added to the dictionary sys.modules
, keyed by the fully qualified name of the module. Future import statements will look in sys.modules
for an existing reference before doing any actual work.
In your case, import alt
will create a module referenced by sys.modules['alt']
as well as by the name alt
in main
. The statement import os
in alt
will be run next. It will create a module referenced by sys.modules['os']
and alt.os
. If you were to add a line import os
in main
after import alt
, it will not create and load another module object. Instead, the name os
will be bound to the same object pointed to by sys.modules['os']
.
The following three versions of main
will all call the same getcwd
function:
Direct import (recommended):
import alt import os print(os.getcwd())
Use the reference in
alt
(harder to read/trace):import alt print(alt.os.getcwd())
Using
sys.modules
(really not recommended for production unless you know what you are doing):import alt # necessary to trigger the actual import import sys print(sys.modules['os'].getcwd())
All imports load a full module. This even applies to imports of the form from os import getcwd
. The module sys.modules['os']
is still created. The only difference is that the importing namespace will only have access to the name getcwd
, not os
. In your case, if alt
contained from os import getcwd
instead of import os
, the three access methods would change as follows:
- Unchanged.
print(alt.getcwd())
sincealt.os
no longer exists.- Unchanged.
回答3:
You are importing os
only in the in the submodul level of alt
. os
is to say so only available by access through alt.os
. A way around this would be to import all from alt as from alt import *
, but this is not what you should do...
As a general rule of thumb, you should re-import your directly called-to modules on the top level of the module that you currently process. thus at main.py:
import os
and everything is fine
回答4:
You write it this way
__author__ = 'kerberos'
__date__ = '2017/10/25 20:48 '
import alt
print(alt.os.getcwd())
This is the result:
C:\Users\Administrator\Desktop\11
来源:https://stackoverflow.com/questions/46932818/using-modules-imported-from-another-import