如何在Python中获取对当前模块属性的引用

gui*_*ooo 111 python

我想要做的就是在命令行中看起来像这样:

>>> import mymodule
>>> names = dir(mymodule)
Run Code Online (Sandbox Code Playgroud)

我怎样才能获得中定义的所有名称引用mymodule从内部mymodule本身?

像这样的东西:

# mymodule.py
names = dir(__thismodule__)
Run Code Online (Sandbox Code Playgroud)

jam*_*sls 148

如前所述,globals为您提供了一个字典而不是dir(),它为您提供了模块中定义的名称列表.我通常看到这样做的方式是这样的:

import sys
dir(sys.modules[__name__])
Run Code Online (Sandbox Code Playgroud)

  • 优秀!这只允许我使用当前模块的docstring作为用法消息 - "sys.modules [__ name __] .__ doc__`. (9认同)
  • 对于任何阅读乔治评论的人: `sys.modules[__name__].__doc__` == `__doc__` 因为这是在当前命名空间中定义的。因此,不需要获取模块对象来访问其自身的属性。 (3认同)
  • 我要添加一条注释,该注释不适用于'__main__'模块(这是在终端上运行的模块所调用的模块),因为它似乎未在sys.modules中列出-但确实可以工作:) (2认同)

Mac*_*cki 126

只需使用全局()

globals() - 返回表示当前全局符号表的字典.这始终是当前模块的字典(在函数或方法内部,这是定义它的模块,而不是调用它的模块).

http://docs.python.org/library/functions.html#globals

  • 您可以尝试从traceback模块(http://docs.python.org/library/traceback.html)获取调用者的全局变量,但这会进入黑暗魔法领域.我不知道你要做什么,但如果你需要,你可能想重新考虑你的设计. (9认同)
  • 有没有办法访问调用模块的gloabals()而不是定义模块? (3认同)

And*_*dry 6

也许现在回答已经晚了,但我自己并没有找到正确的答案。inspect.stack()python 中最接近和精确的解决方案(比 更快) 3.7.x

# search for first module in the stack
stack_frame = inspect.currentframe()
while stack_frame:
  print('***', stack_frame.f_code.co_name, stack_frame.f_code.co_filename, stack_frame.f_lineno)
  if stack_frame.f_code.co_name == '<module>':
    if stack_frame.f_code.co_filename != '<stdin>':
      caller_module = inspect.getmodule(stack_frame)
    else:
      # piped or interactive import
      caller_module = sys.modules['__main__']
    if not caller_module is None:
      #... do something here ...
    break
  stack_frame = stack_frame.f_back
Run Code Online (Sandbox Code Playgroud)

优点

  • 比方法更精确globals()
  • 不依赖于堆栈中间帧,可以通过挂钩或 3dparty 工具添加,例如pytest
*** foo ... ..
*** boo ... ..
*** runtest c:\python\x86\37\lib\site-packages\xonsh\pytest_plugin.py 58
*** pytest_runtest_call c:\python\x86\37\lib\site-packages\_pytest\runner.py 125
*** _multicall c:\python\x86\37\lib\site-packages\pluggy\callers.py 187
*** <lambda> c:\python\x86\37\lib\site-packages\pluggy\manager.py 86
*** _hookexec c:\python\x86\37\lib\site-packages\pluggy\manager.py 92
*** __call__ c:\python\x86\37\lib\site-packages\pluggy\hooks.py 286
*** <lambda> c:\python\x86\37\lib\site-packages\_pytest\runner.py 201
*** from_call c:\python\x86\37\lib\site-packages\_pytest\runner.py 229
*** call_runtest_hook c:\python\x86\37\lib\site-packages\_pytest\runner.py 201
*** call_and_report c:\python\x86\37\lib\site-packages\_pytest\runner.py 176
*** runtestprotocol c:\python\x86\37\lib\site-packages\_pytest\runner.py 95
*** pytest_runtest_protocol c:\python\x86\37\lib\site-packages\_pytest\runner.py 80
*** _multicall c:\python\x86\37\lib\site-packages\pluggy\callers.py 187
*** <lambda> c:\python\x86\37\lib\site-packages\pluggy\manager.py 86
*** _hookexec c:\python\x86\37\lib\site-packages\pluggy\manager.py 92
*** __call__ c:\python\x86\37\lib\site-packages\pluggy\hooks.py 286
*** pytest_runtestloop c:\python\x86\37\lib\site-packages\_pytest\main.py 258
*** _multicall c:\python\x86\37\lib\site-packages\pluggy\callers.py 187
*** <lambda> c:\python\x86\37\lib\site-packages\pluggy\manager.py 86
*** _hookexec c:\python\x86\37\lib\site-packages\pluggy\manager.py 92
*** __call__ c:\python\x86\37\lib\site-packages\pluggy\hooks.py 286
*** _main c:\python\x86\37\lib\site-packages\_pytest\main.py 237
*** wrap_session c:\python\x86\37\lib\site-packages\_pytest\main.py 193
*** pytest_cmdline_main c:\python\x86\37\lib\site-packages\_pytest\main.py 230
*** _multicall c:\python\x86\37\lib\site-packages\pluggy\callers.py 187
*** <lambda> c:\python\x86\37\lib\site-packages\pluggy\manager.py 86
*** _hookexec c:\python\x86\37\lib\site-packages\pluggy\manager.py 92
*** __call__ c:\python\x86\37\lib\site-packages\pluggy\hooks.py 286
*** main c:\python\x86\37\lib\site-packages\_pytest\config\__init__.py 90
*** <module> c:\Python\x86\37\Scripts\pytest.exe\__main__.py 7
Run Code Online (Sandbox Code Playgroud)
  • 可以处理 python 管道或交互式会话。

缺点:

  • 一种非常精确并且可以返回在可执行文件中注册的模块,例如这pytest.exe可能不是您想要的。
  • inspect.getmodule根据挂钩,仍然可能在有效模块上返回 None

我有 python 的扩展: 如何导入给定完整​​路径的模块?

具有针对这种情况的包装函数的扩展:

*** foo ... ..
*** boo ... ..
*** runtest c:\python\x86\37\lib\site-packages\xonsh\pytest_plugin.py 58
*** pytest_runtest_call c:\python\x86\37\lib\site-packages\_pytest\runner.py 125
*** _multicall c:\python\x86\37\lib\site-packages\pluggy\callers.py 187
*** <lambda> c:\python\x86\37\lib\site-packages\pluggy\manager.py 86
*** _hookexec c:\python\x86\37\lib\site-packages\pluggy\manager.py 92
*** __call__ c:\python\x86\37\lib\site-packages\pluggy\hooks.py 286
*** <lambda> c:\python\x86\37\lib\site-packages\_pytest\runner.py 201
*** from_call c:\python\x86\37\lib\site-packages\_pytest\runner.py 229
*** call_runtest_hook c:\python\x86\37\lib\site-packages\_pytest\runner.py 201
*** call_and_report c:\python\x86\37\lib\site-packages\_pytest\runner.py 176
*** runtestprotocol c:\python\x86\37\lib\site-packages\_pytest\runner.py 95
*** pytest_runtest_protocol c:\python\x86\37\lib\site-packages\_pytest\runner.py 80
*** _multicall c:\python\x86\37\lib\site-packages\pluggy\callers.py 187
*** <lambda> c:\python\x86\37\lib\site-packages\pluggy\manager.py 86
*** _hookexec c:\python\x86\37\lib\site-packages\pluggy\manager.py 92
*** __call__ c:\python\x86\37\lib\site-packages\pluggy\hooks.py 286
*** pytest_runtestloop c:\python\x86\37\lib\site-packages\_pytest\main.py 258
*** _multicall c:\python\x86\37\lib\site-packages\pluggy\callers.py 187
*** <lambda> c:\python\x86\37\lib\site-packages\pluggy\manager.py 86
*** _hookexec c:\python\x86\37\lib\site-packages\pluggy\manager.py 92
*** __call__ c:\python\x86\37\lib\site-packages\pluggy\hooks.py 286
*** _main c:\python\x86\37\lib\site-packages\_pytest\main.py 237
*** wrap_session c:\python\x86\37\lib\site-packages\_pytest\main.py 193
*** pytest_cmdline_main c:\python\x86\37\lib\site-packages\_pytest\main.py 230
*** _multicall c:\python\x86\37\lib\site-packages\pluggy\callers.py 187
*** <lambda> c:\python\x86\37\lib\site-packages\pluggy\manager.py 86
*** _hookexec c:\python\x86\37\lib\site-packages\pluggy\manager.py 92
*** __call__ c:\python\x86\37\lib\site-packages\pluggy\hooks.py 286
*** main c:\python\x86\37\lib\site-packages\_pytest\config\__init__.py 90
*** <module> c:\Python\x86\37\Scripts\pytest.exe\__main__.py 7
Run Code Online (Sandbox Code Playgroud)

您必须正确初始化扩展:

def tkl_get_stack_frame_module_by_offset(skip_stack_frames = 0, use_last_frame_on_out_of_stack = False):
  ...

def tkl_get_stack_frame_module_by_name(name = '<module>'):
  ...
Run Code Online (Sandbox Code Playgroud)


DrB*_*ney 5

另请查看内置检查模块.它可以非常方便.

  • 期望相关的使用示例.链接可能腐烂,这里没有任何价值. (16认同)