如何将在 python 文件中导入的库导入到另一个 python 文件中?
How to import libraries imported in a python file into another python file?
我有两个 python 文件。我正在使用其中之一来导入所有先决条件库。我正在使用另一个来执行一些代码。
这是名为 imports.py
的第一个 python 文件
def importAll(process):
import pandas as pd
import numpy as np
import seaborn as sns
import matplotlib.pyplot as plt
print('Success')
if process == 'train':
import sklearn
第二个python文件train.py如下:
from imports import importAll
importAll('train')
def load_data(date):
#load only data till Sep
df = pd.read_csv('df.csv')
return(df[df['date'] < date])
date = '2012-09-01'
df = load_data(date)
当我 运行 train.py 时,请注意 'Success' 正在打印(来自 imports.py 文件)
但是,我也收到未定义 pd 的错误(在 df = pd.read_csv('df.csv') 行中)
有什么办法可以纠正这个错误吗?
当您从函数范围内导入时,该导入仅从该函数内定义,而不是在调用该函数的范围内定义。
我建议查看 this 问题以获得对 python 中范围规则的良好解释。
要解决此问题,您可以使用 python 的 star import.
imports.py:
import pandas as pd
import numpy as np
import seaborn as sns
import matplotlib.pyplot as plt
__all__ = [
'pd',
'np',
'sns',
'plt'
]
train.py:
from imports import *
...
语法 from module import *
从该模块中导入 __all__
列表中定义的所有变量。
编辑
我强烈反对使用此代码,因为它会产生与您预期的相反的效果。这将删除冗余导入语句的 "clutter",代价是更糟糕的事情:混乱的代码和等待浮出水面的隐藏错误(在下面解释)。
唉,解决办法:
import inspect
import pandas as pd
import numpy as np
import seaborn as sns
import matplotlib.pyplot as plt
CODE_CONTEXT = ['from imports import *\n']
__all__ = [
'pd',
'np',
'sns',
'plt'
]
def _get_filename():
frame, *_ = filter(
lambda frame: getattr(frame, 'code_context', None) == CODE_CONTEXT,
inspect.stack()
)
return frame.filename
imported_from = _get_filename()
if imported_from == 'train.py':
import sklearn
__all__.append('sklearn')
elif imported_from == 'eda.py':
...
要了解此代码中可能出现错误的原因,请考虑以下示例:
imports.py:
import inspect
CODE_CONTEXT = ['from imports import *\n']
__all__ = []
def _get_filename():
frame, *_ = filter(
lambda frame: getattr(frame, 'code_context', None) == CODE_CONTEXT,
inspect.stack()
)
return frame.filename
imported_from = _get_filename()
print(imported_from)
a.py:
from imports import *
b.py:
from imports import *
main.py:
import a
import b
当你运行 python3 main.py
控制台会打印什么?
a.py
为什么不打印 b.py
?因为 模块在第一次导入时只执行一次 。由于 a.py
首先导入模块,因此每次后续导入 imports.py
都不会重新执行该模块,它们将重用在初始执行期间构建的代码。
TLDR;
对 __all__
所做的任何更改仅适用于模块的 第一次 导入,后续导入可能会缺少所需的模块。
理想情况下,您应该在 python 类似结构的包中工作,Python 模块默认需要有 __init__.py
文件。在那里,您可以通过 __init__.py
文件将所有其他 files/modules 包含在包中。
假设,你制作包 example
包。 文件结构将是,
- outer.py
- 例子
- 初始化.py
- file1.py
- file2.py
- 包2
- __init.py
如果file1.py
一个有两个类
class A:
def __init__(self):
pass
class B:
def __init__(self):
pass
如果file2.py
一个再有两个类
class C:
def __init__(self):
pass
class D:
def __init__(self):
pass
并且您想在外部文件
中包含所有这些 类
add/import __init__.py
文件中的所有 类,例如
from .file1 import *
from .file2 import *
现在在外部文件中你可以简单地这样做
outer.py
from package import *
# this will import all four A, B, C, D classes here
我有两个 python 文件。我正在使用其中之一来导入所有先决条件库。我正在使用另一个来执行一些代码。 这是名为 imports.py
的第一个 python 文件def importAll(process):
import pandas as pd
import numpy as np
import seaborn as sns
import matplotlib.pyplot as plt
print('Success')
if process == 'train':
import sklearn
第二个python文件train.py如下:
from imports import importAll
importAll('train')
def load_data(date):
#load only data till Sep
df = pd.read_csv('df.csv')
return(df[df['date'] < date])
date = '2012-09-01'
df = load_data(date)
当我 运行 train.py 时,请注意 'Success' 正在打印(来自 imports.py 文件) 但是,我也收到未定义 pd 的错误(在 df = pd.read_csv('df.csv') 行中) 有什么办法可以纠正这个错误吗?
当您从函数范围内导入时,该导入仅从该函数内定义,而不是在调用该函数的范围内定义。
我建议查看 this 问题以获得对 python 中范围规则的良好解释。
要解决此问题,您可以使用 python 的 star import.
imports.py:
import pandas as pd
import numpy as np
import seaborn as sns
import matplotlib.pyplot as plt
__all__ = [
'pd',
'np',
'sns',
'plt'
]
train.py:
from imports import *
...
语法 from module import *
从该模块中导入 __all__
列表中定义的所有变量。
编辑
我强烈反对使用此代码,因为它会产生与您预期的相反的效果。这将删除冗余导入语句的 "clutter",代价是更糟糕的事情:混乱的代码和等待浮出水面的隐藏错误(在下面解释)。
唉,解决办法:
import inspect
import pandas as pd
import numpy as np
import seaborn as sns
import matplotlib.pyplot as plt
CODE_CONTEXT = ['from imports import *\n']
__all__ = [
'pd',
'np',
'sns',
'plt'
]
def _get_filename():
frame, *_ = filter(
lambda frame: getattr(frame, 'code_context', None) == CODE_CONTEXT,
inspect.stack()
)
return frame.filename
imported_from = _get_filename()
if imported_from == 'train.py':
import sklearn
__all__.append('sklearn')
elif imported_from == 'eda.py':
...
要了解此代码中可能出现错误的原因,请考虑以下示例:
imports.py:
import inspect
CODE_CONTEXT = ['from imports import *\n']
__all__ = []
def _get_filename():
frame, *_ = filter(
lambda frame: getattr(frame, 'code_context', None) == CODE_CONTEXT,
inspect.stack()
)
return frame.filename
imported_from = _get_filename()
print(imported_from)
a.py:
from imports import *
b.py:
from imports import *
main.py:
import a
import b
当你运行 python3 main.py
控制台会打印什么?
a.py
为什么不打印 b.py
?因为 模块在第一次导入时只执行一次 。由于 a.py
首先导入模块,因此每次后续导入 imports.py
都不会重新执行该模块,它们将重用在初始执行期间构建的代码。
TLDR;
对 __all__
所做的任何更改仅适用于模块的 第一次 导入,后续导入可能会缺少所需的模块。
理想情况下,您应该在 python 类似结构的包中工作,Python 模块默认需要有 __init__.py
文件。在那里,您可以通过 __init__.py
文件将所有其他 files/modules 包含在包中。
假设,你制作包 example
包。 文件结构将是,
- outer.py
- 例子
- 初始化.py
- file1.py
- file2.py
- 包2
- __init.py
如果file1.py
一个有两个类
class A:
def __init__(self):
pass
class B:
def __init__(self):
pass
如果file2.py
一个再有两个类
class C:
def __init__(self):
pass
class D:
def __init__(self):
pass
并且您想在外部文件
中包含所有这些 类add/import __init__.py
文件中的所有 类,例如
from .file1 import *
from .file2 import *
现在在外部文件中你可以简单地这样做 outer.py
from package import *
# this will import all four A, B, C, D classes here