Python:检查导入模块时出现运行时错误的原因是什么?

标签 python python-3.x python-2.7

我想做什么:

检查我在脚本中导入的不同模块(Python 2 或 3),并打印它们的名称。我目前使用的是 Python 2.7.12 和 3.6.4。

我从哪里开始:

该脚本只是导入模块,使用列表理解来查找其中的内容,然后打印列表:

#!/usr/bin/env python

import sys
import os
import types

module_list = [i.__name__ for i in globals().values()
               if type(i) == types.ModuleType and i in sys.modules.values()]
print(module_list)

我最初是在 Python 3 中运行它,它运行得很好(对于 Python 2 也很好)。输出为:

['__builtin__', 'sys', 'os', 'types']  # Python 2.
['builtins', 'sys', 'os', 'types']     # Python 3.

此时,我决定扩展列表理解,因为我发现它是破译代码/逻辑流的良好实践。所以我将单个语句替换为:

module_list = []
for i in globals().values():
    if type(i) == types.ModuleType and i in sys.modules.values():
        module_list.append(i.__name__)

这就是事情变得棘手的地方。我收到一个 RuntimeError,现在的输出是:

...
    for i in globals().values():
RuntimeError: dictionary changed size during iteration

但是,它在 Python 2 中仍然有效。我现在比其他任何事情都更好奇,并尝试了一些事情。

我尝试过的:

  • globals().values() 转换为列表:

    for i in list(globals().values()):
        if type(i) == types.ModuleType and i in sys.modules.values():
            module_list.append(i.__name__)
    

    这在 Python 2 或 3 中按预期工作。

  • 删除了 list() 并添加到正确的 main 结构中:

    def main():
        module_list = []
        for i in globals().values():
            if type(i) == type(sys) and i in sys.modules.values():
                module_list.append(i.__name__)
        print(module_list)
    
    if __name__ == '__main__':
        main()
    

    这在 Python 2 和 3 中按预期工作。

回顾一下:

  • 列表理解适用于 Python 2 和 3。
  • for 循环仅适用于 Python 2。
  • 包装在列表中适用于Python 2和3。
  • 正确的 main 结构适用于 Python 2 和 3。

问题:

Python 3 中的 for 循环破坏了什么?

最佳答案

for i in globals().values(): - 在获取 values 迭代器后,i 将添加到全局命名空间。如果您将 i = None 放在循环之前,或者执行 for i in list(globals().values()):,它就会起作用。

在 python 2 中,values() 返回一个值列表,但在 python 3 中它是一个迭代器。该迭代器检测到更改并引发错误。

关于Python:检查导入模块时出现运行时错误的原因是什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49563728/

相关文章:

python - 未正确调用 DataFrame 构造函数

string - python : remove single quotation in a string in a list

python - 在 Python 中读取非结构化文本文件以使其结构化

python - 使用 Pip 安装 Flask

python - 使用 BeautifulSoup 4 提取日期

python - python逆向工程后没有关系的类图

python 多行不能与/运算符一起使用

python - 使用 Python 无浏览器访问 LinkedIn

python-3.x - BeautifulSoup 发现所有表都是空的

python-2.7 - 使用 python cv2 播放视频