[英]Plotly.py bug using discrete colour data on stacked bar chart with customdata in hover text
我有一个 Pandas DataFrame, df
,我用它来填充 Plotly 条形图。 为了举例,让我们定义df
如下:
import pandas, numpy
import plotly.express as px
df = pandas.DataFrame.from_dict(
{
"x": ["John Cleese", "Eric Idle", "Michael Palin", "Eric Idle"],
"y": [7, 10, 3, 8],
"colour": ["0", "0", "0", "1"],
"a": [1, 2, 3, 4],
"b": [1, 4, 9, 16],
"c": [1, 8, 27, 64]
}
)
并创建从这些数据派生的条形图
fig = px.bar(df, x="x", y="y", color="colour", barmode="stack")
my_customdata = numpy.transpose(numpy.array([df["a"], df["b"], df["c"]]))
fig = fig.update_traces(
patch={
"customdata": my_customdata,
"hovertemplate": "x: %{x}, y: %{y}, a: %{customdata[0]}, b: %{customdata[1]}, c: %{customdata[2]}<extra></extra>"
},
overwrite=True
)
fig.update_layout(
xaxis={"categoryorder": "total ascending"}
)
fig.show()
该错误出现在红色堆叠条的 hover 文本中。 您会注意到customdata
文本中的x
和y
数据是正确的,但自定义数据产生的数据不是!
有趣的是,只有当传递给px.bar()
的color
参数的Pandas.Series
object 由字符串数据(即离散颜色数据)组成时,才会出现此错误。 如果在上面的代码中我改为设置df.colour = [0, 0, 0, 1]
(使用整数表示连续的颜色数据,请注意颜色条),则会创建以下图表:
我的项目需要使用离散颜色数据,是否有解决此错误的方法?
事实证明解决方案相对简单,是我的错而不是源代码本身的问题(哦,认为这不是我的错的狂妄自大!)
在运行px.bar()
时, plotly.express
创建一个plotly.graph_objs.Figure
。图 object 包含两个Bar
对象,而不是一个。 然后,当调用customdata
fig.update_traces()
时,自定义数据将应用于作为fig
子对象的所有Bar
对象。 Red Eric Idle 是原始 DataFrame 的第 4 个值,但是fig.update_traces()
不关心 Red Eric Idle曾经在哪里 - 它只知道现在它是第二个Bar
object 的一部分。事实上,Red Eric Idle 是此Bar
的第一个数据点 object,因此愉快地使用customdata[0][n]
、 customdata[1][n]
、 customdata[2][n]
创建悬停文本数据,其中n=0
(第一个值),而不是像我预期的那样使用n=3
(第四个值)。
这就是为什么 Red Eric Idle 的 hover 文本包含"a: 1, b: 1, c: 1"
,而不是"a: 4, b: 16:, c: 64"
。
解决方案非常简单。 由于 Plotly 图在完成运行px.bar()
后“忘记”了原始 DataFrame 中每个点的数据应该为 go 的位置,我们只需在每个数据点忘记之前(即在px.bar()
电话. 只需更换
fig = px.bar(df, x="x", y="y", color="colour", barmode="stack")
my_customdata = numpy.transpose(numpy.array([df["a"], df["b"], df["c"]]))
fig = fig.update_traces(
patch={
"customdata": my_customdata,
"hovertemplate": "x: %{x}, y: %{y}, a: %{customdata[0]}, b: %{customdata[1]}, c: %{customdata[2]}<extra></extra>"
},
overwrite=True
)
和
fig = px.bar(
df, x="x", y="y", color="colour", barmode="stack", custom_data=["a", "b", "c"]
)
fig = fig.update_traces(
patch={
"hovertemplate": "x: %{x}, y: %{y}, a: %{customdata[0]}, b: %{customdata[1]}, c: %{customdata[2]}"
},
overwrite=True
)
嘿 presto,Red Eric Idle 突然有了 hover 文本,其中包含4, 16, 64
而不是1, 1, 1
:
首先,这也是更简洁的代码。 在原始的 Plotly 示例文档中,我并不明显可以在custom_data
模块中像这样分配plotly.express
。
但是,当我们设置df.colour = [0, 0, 0, 1]
时,为什么这种奇怪的行为 go 消失了?
原因是当px.bar()
传入连续的颜色数据时,它只为每个图形创建一个Bar
object。 在这种情况下, Bar
中的每个数据点都会记住其在 DataFrame 中的行customdata
,因此自定义数据的分配就像一个魅力。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.