【问题标题】:Bokeh updates the legend but not the scatterplot elements散景更新图例但不更新散点图元素
【发布时间】:2019-09-10 05:31:28
【问题描述】:

我需要展示一个从 DataFrame 构建的动态散点图。用户应该能够在多个类别中选择要显示的类别(或显示所有类别)。我让 Bokeh 更新了显示可能类别的图例,而不是标记本身。

我已经在 J​​upyter 笔记本和 Bokeh 服务器上尝试过代码,它们的行为是相同的。我还尝试在不同的浏览器(Chrome、Firefox,甚至是优秀的 Internet Explorer)上运行代码,但没有骰子。

这是我正在做的事情的 sn-p,其中df 是一个 Pandas DataFrame,其中包含 ClientClient SectorVolumeProfit Margin 列,其想法是绘制两个卷和边距:

SECTORS = list(df["Client Sector"].unique())

tools = ["box_select", "hover", "reset", "box_zoom", "wheel_zoom", "pan"]

TOOLTIPS = [
    ("Client", "@Client"),
    ("Activity", "@{Client Sector}"),
    ("Volume", "@Volume"),
    ("Margin", "@{Profit Margin}")
]

source = ColumnDataSource(data = df)


p = figure(plot_width=1600, plot_height=800, tools=tools, tooltips=TOOLTIPS)
r = p.circle('Volume', 'Profit Margin', source=source, size=10, 
         color=factor_cmap('Client Sector', 'Category10_7', SECTORS), 
         alpha=0.5, legend='Client Sector', hover_color='black')

def update():
    sector_val = sector.value
    if sector_val == "All":
        selected = df
    else:
        selected = df[df["Client Sector"] == sector_val]
    source = ColumnDataSource(data=selected)
    r.data_source = source

sector = Select(title="Sector", value="All", options=["All"] + SECTORS)

sector.on_change('value', lambda attr, old, new: update())

update()

curdoc().add_root(row(ativ, p))

正如预期的那样,这会生成一个散点图,其中包含根据客户所在行业着色的标记,以及行业及其颜色的图例。用于选择单个扇区的小部件也在那里。但是,当我选择单个扇区时,图例会发生变化(剩余扇区的颜色变为蓝色,即原始图例中第一个扇区的颜色),但标记及其颜色保持不变(尽管悬停工具停止工作)。

【问题讨论】:

    标签: python pandas bokeh


    【解决方案1】:

    Bokeh ColumnDataSource 对象非常重量级,与许多其他对象有联系。基本上不支持批发更换。每个示例或文档 sn-p 始终且仅显示通过更新其 .data 属性来更新现有 CDS,这就是您应该使用的方式:

    r.data_source.data = selected
    

    最新版本支持直接从 DataFrame 进行设置。否则,您可以在 CDS 上显式调用 data_from_df 静态方法。

    【讨论】:

    • 抱歉,我应该提到我正在使用 Bokeh 1.2.0(这是我在工作中使用的,来自 Windows 上的 Conda 4.7.10)。我尝试用r.data_source.from_df(selected) 替换您提到的行,但它不起作用(data_from_df 抛出一个 AttributeError)。我应该以不同的方式初始化 CDS 吗?感谢您的帮助!
    • 应该更明确:“没用” = 选择不同的部门不会改变任何事情(甚至是传说)。
    • 好的,刚刚知道我应该使用r.data_source.data = ColumnDataSource.from_df(selected)。谢谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-06-23
    • 2021-04-23
    • 1970-01-01
    • 1970-01-01
    • 2018-10-22
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多