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

如何在Bokeh中移除无对应数据的日期并消除图表长连线?

解决Bokeh图表中无数据日期的长连线问题

核心原因

当时间序列数据中存在**日期间隔过大(无匹配数据)**的情况时,Bokeh的line方法会直接连接前后两个有效数据点,从而产生横跨无数据日期的长连线。

可行解决方案

方案1:用NaN中断连线(推荐)

在数据中检测到前后两个数据点的时间间隔超过阈值时,插入NaN值,Bokeh绘制线时会自动在NaN位置断开连线。

修改代码步骤:

  1. 用Pandas处理DataFrame,计算相邻日期的时间间隔
  2. 在间隔超阈值的位置插入NaN中断连线
  3. 重新生成数据源

修改后的完整代码:

def get(self, request):
    user=request.user
    historical_me=FinancialInstrument.objects.all()
    form = self.form_class(historical_me=historical_me)
    
    retrive=HistoricalData.objects.all()
    get_symbol=retrive.filter(instrument__symbol="BTUSD").order_by('datetime')
    fields=get_symbol.values('datetime','opening_price','closing_price','min_price','max_price','volume')
    df=pd.DataFrame.from_records(fields)
    
    # 转换datetime为Pandas可处理的时间类型
    df['datetime'] = pd.to_datetime(df['datetime'])
    # 计算相邻数据点的时间间隔(单位:小时)
    df['time_diff'] = df['datetime'].diff().dt.total_seconds() / 3600
    
    # 设定正常时间间隔阈值(可根据数据更新频率调整,日级数据设为24)
    threshold = 24
    x_values = []
    y_values = []
    for idx, row in df.iterrows():
        x_values.append(row['datetime'])
        y_values.append(float(row['opening_price']))
        # 非最后一行且间隔超阈值时,插入NaN中断连线
        if idx < len(df)-1 and df.loc[idx+1, 'time_diff'] > threshold:
            x_values.append(None)
            y_values.append(None)
    
    source = ColumnDataSource(data=dict(dater=x_values,pricer=y_values))
    plot = figure(title="New title", width=780, height=400,
                  x_axis_label="Date", y_axis_label="Max Price", x_axis_type="datetime")
    plot.line(x='dater',y='pricer', source=source,line_width=3)
    
    plot.toolbar.autohide = True

    script, div = components(plot)
    if user.is_authenticated:
        return render(
            request,
            self.template_name,
            {
                'form':form,
                'days_of_month': [i for i in range(1,32)],
                'script':script,
                'div':div,
            })

    return redirect('home')

方案2:分割连续时间区间绘制多段线

将数据分割为多个连续的时间子序列,使用multi_line分别绘制每个子序列的线,不同子序列之间不会产生跨无数据日期的连线。

方案3:过滤非连续数据

如果只需要展示连续的时间区间,可以直接筛选出无间隔的连续数据段进行绘制,跳过存在大间隔的部分。

额外注意事项

  • 原代码中重复调用的plot.line(x='datetime', y='opening_price', source=source)会报错,因为source中不存在datetime和opening_price字段,建议删除该行。
  • 阈值threshold需根据实际数据更新频率调整(比如小时级数据可设为1)。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.25 14:05:06