You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过编程更新Bokeh数据源选中索引并触发视图重绘?

解决Bokeh编程方式设置选中点不更新的问题

我明白你遇到的困扰了——直接用source.selected.update(indices=[4])确实只会修改属性值,但不会触发Bokeh的变更事件,导致图表没重绘、回调函数也没执行。这是因为Bokeh的模型属性(比如Selection的indices)是通过专门的属性系统来追踪变化的,普通的字典更新方法绕开了这个系统,自然不会触发后续的更新逻辑。

正确的解决方法

你只需要直接给source.selected.indices赋值,而不是用update方法:

def update_selection_programmatically():
    source.selected.indices = [4]  # 直接赋值触发属性变更事件

为什么这样可行?

Bokeh的ColumnDataSource和Selection都是Bokeh模型对象,它们的属性变更会被内部的属性系统实时监听。当你直接对indices属性赋值时,系统会自动检测到变化,同步触发两个关键行为:

  • 重绘图表,将目标点标记为选中状态
  • 调用你通过source.on_change('selected', update_selection)注册的回调函数

修改后的完整代码

from bokeh.io import curdoc
from bokeh.models import ColumnDataSource
from bokeh.plotting import figure
from bokeh.layouts import column
from bokeh.models.tools import LassoSelectTool, TapTool
from bokeh.models.widgets.buttons import Button

source = ColumnDataSource(dict(
    x=[1, 2, 3, 4, 5, 6],
    y=[1, 2, 3, 4, 5, 6],
))

p = figure(
    plot_height=300,
    tools='',
)
p.circle(
    x='x', y='y', size=20, source=source)

lasso_select = LassoSelectTool(
    select_every_mousemove=False,
)
tap = TapTool()
tools = (lasso_select, tap)
p.add_tools(*tools)

def update_selection_programmatically():
    source.selected.indices = [4]  # 改为直接赋值触发更新

bt = Button(
    label="Update Selection", button_type="success", width=50
)
bt.on_click(update_selection_programmatically)

def update_selection(attr, old, new):
    print('>> NEW SELECTION: {}'.format(new.indices))

source.on_change('selected', update_selection)

curdoc().add_root(column([p, bt]))

现在点击按钮后,索引为4的点会被正确标记为选中,同时控制台也会打印出选中的索引信息,完全符合你的预期~

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

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 08:13:07