如何在Plotly时间序列折线图中添加推文散点标记并修复悬停文本问题
Plotly 时间序列折线图添加推文标记散点问题
需求
在doge、btc、eth、shib四个加密货币收盘价的时间序列折线图上,对有推文发布的时间点添加散点标记,悬停时可查看推文内容、是否关注等字段。
现存问题
- 初始版本用
px.line按has_tweet染色,仅生成has_tweet=1的折线,无法在对应时间点展示散点标记 - 第二版用
add_trace添加go.Scatter散点图层时存在索引语法错误,且悬停文本仅显示日期和价格,无法展示推文相关字段 - 第三版配置
hovertemplate时,text参数的列表推导逻辑错误,把布尔判断结果当作内容传入,无法正确显示非空推文内容
现有代码版本
初始代码
fig = px.line(total_data, x = 'date', y = ['doge_close','btc_close','eth_close','shib_close'], color = 'has_tweet', hover_data = ['content', 'of_interest'] ) fig.show()
第二版调整代码
fig = px.line(total_data, x = total_data.date, y = total_data.doge_close) fig.add_trace( go.Scatter( x=total_data[total_data.has_tweet==1].date, y=total_data[total_data.has_tweet == 1['doge_close'], mode = 'markers', name = 'Tweet', hovertext = ['content', 'of_interest'])) fig.show()
第三版悬停模板配置代码
fig = px.line(total_data, x = total_data.date, y = total_data.doge_close) fig.add_trace( go.Scatter( x=total_data[total_data.has_tweet==1].date, y=total_data[total_data.has_tweet == 1['doge_close'], mode = 'markers', hovertemplate = '<i>tweet:</i>'+ '<br>' + '<i>%{text}</i>', text = [t for t in total_data['content'] != 'NaN'], name = 'has_tweets')) fig.show()
修正方案
核心修正点
- 先单独提取
has_tweet=1的数据集,避免重复写筛选逻辑,同时修正索引语法错误 - 用
customdata传入多字段悬停内容,不需要写冗余的列表推导 - 可以根据需求选择单币种或四币种实现方案
单币种(DOGE)实现代码
import plotly.express as px import plotly.graph_objects as go # 提取有推文的子集 tweet_df = total_data[total_data['has_tweet'] == 1].reset_index(drop=True) # 绘制基础折线图 fig = px.line(total_data, x='date', y='doge_close', labels={'doge_close': 'DOGE收盘价'}) # 添加推文标记散点 fig.add_trace( go.Scatter( x=tweet_df['date'], y=tweet_df['doge_close'], mode='markers', marker=dict(size=8, color='red', symbol='star'), name='推文事件', hovertemplate='<b>日期</b>: %{x}<br>' + '<b>DOGE收盘价</b>: %{y}<br>' + '<b>推文内容</b>: %{customdata[0]}<br>' + '<b>是否关注</b>: %{customdata[1]}<extra></extra>', customdata=tweet_df[['content', 'of_interest']].values ) ) fig.show()
四币种完整实现代码
import plotly.express as px import plotly.graph_objects as go coin_list = ['doge_close', 'btc_close', 'eth_close', 'shib_close'] coin_name_map = { 'doge_close': 'DOGE', 'btc_close': 'BTC', 'eth_close': 'ETH', 'shib_close': 'SHIB' } # 提取有推文的子集 tweet_df = total_data[total_data['has_tweet'] == 1].reset_index(drop=True) # 绘制四个币种的基础折线图 fig = px.line(total_data, x='date', y=coin_list, labels={'value': '收盘价', 'variable': '币种'}) # 给每个币种添加对应的推文标记散点 for coin in coin_list: fig.add_trace( go.Scatter( x=tweet_df['date'], y=tweet_df[coin], mode='markers', marker=dict(size=8, symbol='star'), name=f'{coin_name_map[coin]}推文事件', hovertemplate='<b>日期</b>: %{x}<br>' + f'<b>{coin_name_map[coin]}收盘价</b>: %{y}<br>' + '<b>推文内容</b>: %{customdata[0]}<br>' + '<b>是否关注</b>: %{customdata[1]}<extra></extra>', customdata=tweet_df[['content', 'of_interest']].values, showlegend=False # 不需要每个币种散点单独显示图例可保留该配置,需要单独显示删掉即可 ) ) fig.show()
内容的提问来源于stack exchange,提问作者jd_h2003
相关产品推荐
相关产品推荐

