在Jupyter Notebook中使用Joblib时不显示打印输出

Zac*_*mzi 5 python printing joblib jupyter jupyter-notebook

因此,我正在使用joblib来并行化一些代码,并且我注意到在jupyter笔记本中使用它时无法打印内容。

我尝试在ipython中使用相同的示例,但效果很好。

这是在jupyter笔记本单元中编写的最小(非)工作示例

from joblib import Parallel, delayed
Parallel(n_jobs=8)(delayed(print)(i) for i in range(10))
Run Code Online (Sandbox Code Playgroud)

所以我得到的输出,[None, None, None, None, None, None, None, None, None, None]但什么都没有打印。

实际上,在检查笔记本进程的日志时,我注意到打印在那里进行。我希望打印发生在笔记本中,而不是笔记本过程的日志中。

编辑

我已经打开了一个Github问题,但是到目前为止关注的很少。

Z4-*_*ier 9

我认为这部分是由于Parallel产生子工作者的方式以及 Jupyter Notebook 如何为这些工作者处理 IO 造成的。当启动时没有为 指定值backendParallel将默认loky使用池化策略,该策略直接使用 fork-exec 模型来创建子进程。

如果您使用终端从终端启动 Notebook

$ jupyter-notebook
Run Code Online (Sandbox Code Playgroud)

常规stderrstdout流似乎仍然连接到该终端,而笔记本会话将在新的浏览器窗口中启动。在笔记本运行发布的代码片段确实会产生预期的输出,但它似乎进入stdout并最终进入终端(如问题中的注释所示)。这进一步支持了这种行为是由loky和 notebook之间的交互以及 notebook 为子进程处理标准 IO 流的方式引起的怀疑。

这让我在 github 上进行了讨论(截至发帖时的过去 2 周内处于活跃状态),notebook 的作者似乎意识到了这一点,但目前似乎没有明显且快速的解决方案.

如果您不介意切换Parallel用于生成子项的后端,您可以这样做:

from joblib import Parallel, delayed
Parallel(n_jobs=8, backend='multiprocessing')(delayed(print)(i) for i in range(10))
Run Code Online (Sandbox Code Playgroud)

使用multiprocessing后端,事情按预期工作。threading看起来也很好用。这可能不是您希望的解决方案,但希望在笔记本作者努力寻找合适的解决方案时就足够了。

我会将这个交叉发布到 GitHub,以防有人愿意添加到这个答案中(我不想误报任何人的意图或把话放在人们的嘴里!)。


测试环境:
MacOS - Mojave (10.14)
Python - 3.7.3
pip3 - 19.3.1

在 2 种配置中测试。证实了同时使用时产生预期的输出multiprocessing,并threadingbackend参数。使用pip3.

设置 1:

ipykernel                               5.1.1
ipython                                 7.5.0
jupyter                                 1.0.0
jupyter-client                          5.2.4
jupyter-console                         6.0.0
jupyter-core                            4.4.0
notebook                                5.7.8
Run Code Online (Sandbox Code Playgroud)

设置 2:

ipykernel                               5.1.4
ipython                                 7.12.0
jupyter                                 1.0.0
jupyter-client                          5.3.4
jupyter-console                         6.1.0
jupyter-core                            4.6.2
notebook                                6.0.3
Run Code Online (Sandbox Code Playgroud)

我也成功使用了与“Setup 2”相同的版本,但notebook包版本降级到 6.0.2。

笔记:

这种方法在 Windows 上不一致。不同的软件版本组合会产生不同的结果。做最直观的事情——将所有东西升级到最新版本——并不能保证它会起作用。

  • 我使用的是 Windows,这实际上可能是区别。 (2认同)
  • 我确认它可以在 Linux 上运行。我想我们发现了另一个仅与 Windows 相关的错误。请更新您的答案以提及这一点。感谢您的帮助,这个问题让我很头疼!:-) (2认同)

Zac*_*mzi 0

该问题已在最新版本中修复ipykernel。要解决问题就这样做pip install --upgrade ipykernel

据我了解,任何 6 以上的版本都可以,正如一位维护者在Github 评论中提到的那样。