You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

在IPython/Jupyter Notebook线程中调用display渲染HTML报错求助

在IPython Notebook子线程中使用display方法报错的解决办法

你遇到的问题很典型——IPython的display API不是线程安全的,它依赖于主线程的IPython上下文环境,直接在子线程里调用会因为缺少必要的运行上下文抛出异常。

先看看你的代码:

def foo():
    display(HTML('<div id="foobar">foobarbaz</div>'))
threading.Thread(target=foo).start()

对应的错误信息:

Exception in thread Thread-17:
Traceback (most recent call last):
  File "/usr/lib/python3.5/threading.py", line 914, in _bootstrap_inner
    self.run()
  File "/usr/lib/python3.5/threading.py", line 862, in run
    self._target(*self._args, **self._kwargs)
  File "<...>

下面给你两种可行的解决思路:

方法一:借助IPython的主线程调用API

IPython内核提供了invoke_in_main_thread方法,可以把需要执行的display操作调度到主线程中运行,这样就能获取到必要的上下文了:

import threading
from IPython.display import display, HTML

def foo():
    # 先创建HTML对象
    html_content = HTML('<div id="foobar">foobarbaz</div>')
    # 调用主线程执行display
    get_ipython().kernel.invoke_in_main_thread(display, html_content)

threading.Thread(target=foo).start()

方法二:使用ipywidgets的Output组件

如果你已经在使用ipywidgets,Output组件是线程安全的,可以通过它的上下文管理器在子线程中安全输出内容:

import threading
from IPython.display import display, HTML
from ipywidgets import Output

# 先在主线程创建并显示Output组件
output_widget = Output()
display(output_widget)

def foo():
    # 使用Output的上下文管理器包裹display操作
    with output_widget:
        display(HTML('<div id="foobar">foobarbaz</div>'))

threading.Thread(target=foo).start()

这两种方法都能解决子线程中调用display报错的问题,你可以根据自己的场景选择合适的方式~

内容的提问来源于stack exchange,提问作者kotakotakota

火山引擎 最新活动