微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

在实例化队列之前缺少 multiprocessing.queue 模块

如何解决在实例化队列之前缺少 multiprocessing.queue 模块

我正在为女巫 Queues 工作,一切似乎都很顺利。但是,我发现一种情况会导致意外的 AttributeError 异常出现。

让我们创建最简单的代码来创建 Queue。不用担心它的用法,这一切都发生在同一端,我们不必担心另一端会与之通信。

import multiprocessing

q = multiprocessing.Queue()
print(type(q))

代码将作为输出产生:

<class 'multiprocessing.queues.Queue'>

但是如果我尝试确定对象是否是此类的实例会发生什么?

isinstance(q,multiprocessing.queues.Queue)

显然它返回 True

最后,我的问题由此而产生,如果我在检查之前不创建 Queue 实例,则不会加载定义了 multiprocessing.queues 的模块 Queue! (警告,因为我们谈论的是模块,所以这里可能不适合使用加载这个词。我不是这方面的专家)让我们检查一下:

import multiprocessing

a = dict()
isinstance(a,multiprocessing.queues.Queue)

出乎意料的是我们失败的地方:

 1 isinstance(a,multiprocessing.queues.Queue)

AttributeError: module 'multiprocessing' has no attribute 'queues'

为什么会这样?这是预期的行为还是这种错误

对我来说,这代表了一个问题,因为如果我想检查一个对象是否是 Queue 而它不是,如果没有其他队列被实例化,我的检查可能以不希望的 AttributeError 结束.

最后,我想添加一张快速图片,其中包含一些我复制的检查结果,并为 queues 内的 multiprocessing.__all__ 模块添加了一些检查。

这些检查已在 Python 3.9.1 中执行。值得注意的是,当 multiprocessing.queues 已经被识别并因此检查没有抛出 AttributeError 时,queues 出现在 multiprocessing.__dict__ 中。在其他情况下,则不是。

这对专家来说似乎很自然,因为 __dict__ 是(AFAIK)属性列表,但我想指出它,因为我说过我不是专家,我不知道它的实际影响。

enter image description here

附注。我已将问题标记Python 3.8,因为它已经在 3.83.9 中进行了测试并得到了相同的结果,如果存在差异,我希望得到 {{1} 的答案}.这些差异可能是由于多处理库的变化而出现的,因为文档反映在函数末尾的几个脚注中。

PS.2。由于 3.8输出,我一直将 multiprocessing.queues 称为模块。再说一次,我不是这方面的专家:

multiprocessing.__dict__

解决方法

这是有意的行为。如果你想访问一个子模块,你应该导入它:

import multiprocessing.queues

a = dict()
isinstance(a,multiprocessing.queues.Queue)

导入子模块会将它们作为属性添加到其父模块中 – 请注意 multiprocessing.queues.Queue 是如何在 Queue 上的 queue 上的 queue 上的嵌套属性查找 multiprocessing .显式导入可确保在访问子模块之前加载它。

导入系统:5.4.2. Submodules

当使用任何机制(例如 importlib API、importimport-from 语句或内置 __import__())加载子模块时,绑定被放置在父模块的命名空间到子模块对象。例如,如果包 spam 有一个子模块 foo,那么在导入 spam.foo 后,spam 将有一个属性 foo 绑定到子模块。>

这意味着当另一个操作作为副作用导入子模块时,可以避免跳过显式导出。与所有副作用一样,人们必须实际执行触发动作才能依赖副作用。

由于导入是幂等的(重复导入不会产生不良影响),因此应该导入任何希望访问的模块,而不是依赖其他代码的副作用。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。