如何在 altair 中制作分组的多条时间序列图表,底部有日期,图例或弹出窗口中有列标签?
How to make a grouped multibar time series chart in altair with DATE on the bottom and Column labels in a legend or popup?
例如,您可能需要这样的数据:
DATE,KEY,VALUE
2019-01-01,REVENUE,100
2019-01-01,COST,100.1
...
绘制为时间序列条形图,条形之间几乎没有 space,除日期外没有标签。弹出窗口或图例会向您显示 REV、COST 列是什么。
带有 alt.Column、alt.X、alt.Y 的基本条形图可以工作,但标签和分组是错误的。是否可以让Column groups对应x轴,隐藏X轴标签?
编辑:
最新最佳:
import altair as alt
import pandas as pd
m = 100
data = pd.DataFrame({
'DATE': pd.date_range('2019-01-01', freq='D', periods=m),
'REVENUE': np.random.randn(m),
'COST': np.random.randn(m),
}).melt('DATE', var_name='KEY', value_name='VALUE')
bars = alt.Chart(data, width=10).mark_bar().encode(
y=alt.Y('VALUE:Q', title=None),
x=alt.X('KEY:O', axis=None),
color=alt.Color('KEY:O', scale=alt.Scale(scheme='category20')),
tooltip=['DATE', 'KEY', 'VALUE'],
)
(bars).facet(
column=alt.Column(
'yearmonthdate(DATE):T', header=alt.Header(labelOrient="bottom",
labelAngle=-45,
format='%b %d %Y'
)
),
align="none",
spacing=0,
).configure_header(
title=None
).configure_axis(
grid=False
).configure_view(
strokeOpacity=0
)
另一个 post 因为我似乎无法将多个图像添加到原始图像。
这是另一种方法,但有另一个缺陷:条形重叠。但是请注意日期已正确处理,因为这是使用实际轴。
import altair as alt
import pandas as pd
import numpy as np
m = 250
data = pd.DataFrame({
'DATE': pd.date_range('2019-01-01', freq='D', periods=m),
'REVENUE': np.random.randn(m),
'COST': np.random.randn(m),
}).melt('DATE', var_name='KEY', value_name='VALUE')
# Create a selection that chooses the nearest point & selects based on x-value
nearest = alt.selection(type='single', nearest=True, on='mouseover',
fields=['REVENUE'], empty='none')
# The basic line
line = alt.Chart(data).mark_bar(interpolate='basis').encode(
x='DATE:T',
y='VALUE:Q',
color='KEY:N'
).configure_bar(opacity=0.5)
line
您可以结合使用编码和构面来创建分组条形图,并且可以调整轴标题和刻度来自定义外观。这是一个示例(正如您在评论中提到的,在 Altair 中复制 https://vega.github.io/editor/#/examples/vega/grouped-bar-chart):
import altair as alt
import pandas as pd
data = pd.DataFrame([
{"category":"A", "position":0, "value":0.1},
{"category":"A", "position":1, "value":0.6},
{"category":"A", "position":2, "value":0.9},
{"category":"A", "position":3, "value":0.4},
{"category":"B", "position":0, "value":0.7},
{"category":"B", "position":1, "value":0.2},
{"category":"B", "position":2, "value":1.1},
{"category":"B", "position":3, "value":0.8},
{"category":"C", "position":0, "value":0.6},
{"category":"C", "position":1, "value":0.1},
{"category":"C", "position":2, "value":0.2},
{"category":"C", "position":3, "value":0.7}
])
text = alt.Chart(data).mark_text(dx=-10, color='white').encode(
x=alt.X('value:Q', title=None),
y=alt.Y('position:O', axis=None),
text='value:Q'
)
bars = text.mark_bar().encode(
color=alt.Color('position:O', legend=None, scale=alt.Scale(scheme='category20')),
)
(bars + text).facet(
row='category:N'
).configure_header(
title=None
)
原答案:
我无法准确地从你的问题中解析出你想要做什么(将来请考虑包含一个代码片段来展示你已经尝试过的内容并指出结果不充分的原因),但这里是包含这种形式数据的条形图示例,x 轴仅标有日期,工具提示和图例显示收入和成本:
import altair as alt
import pandas as pd
data = pd.DataFrame({
'DATE': pd.date_range('2019-01-01', freq='D', periods=4),
'REVENUE': [100, 200, 150, 50],
'COST': [150, 125, 75, 80],
}).melt('DATE', var_name='KEY', value_name='VALUE')
alt.Chart(data).mark_bar().encode(
x='yearmonthdate(DATE):O',
y='VALUE',
color='KEY',
tooltip=['KEY', 'VALUE'],
)
例如,您可能需要这样的数据:
DATE,KEY,VALUE
2019-01-01,REVENUE,100
2019-01-01,COST,100.1
...
绘制为时间序列条形图,条形之间几乎没有 space,除日期外没有标签。弹出窗口或图例会向您显示 REV、COST 列是什么。
带有 alt.Column、alt.X、alt.Y 的基本条形图可以工作,但标签和分组是错误的。是否可以让Column groups对应x轴,隐藏X轴标签?
编辑:
最新最佳:
import altair as alt
import pandas as pd
m = 100
data = pd.DataFrame({
'DATE': pd.date_range('2019-01-01', freq='D', periods=m),
'REVENUE': np.random.randn(m),
'COST': np.random.randn(m),
}).melt('DATE', var_name='KEY', value_name='VALUE')
bars = alt.Chart(data, width=10).mark_bar().encode(
y=alt.Y('VALUE:Q', title=None),
x=alt.X('KEY:O', axis=None),
color=alt.Color('KEY:O', scale=alt.Scale(scheme='category20')),
tooltip=['DATE', 'KEY', 'VALUE'],
)
(bars).facet(
column=alt.Column(
'yearmonthdate(DATE):T', header=alt.Header(labelOrient="bottom",
labelAngle=-45,
format='%b %d %Y'
)
),
align="none",
spacing=0,
).configure_header(
title=None
).configure_axis(
grid=False
).configure_view(
strokeOpacity=0
)
另一个 post 因为我似乎无法将多个图像添加到原始图像。
这是另一种方法,但有另一个缺陷:条形重叠。但是请注意日期已正确处理,因为这是使用实际轴。
import altair as alt
import pandas as pd
import numpy as np
m = 250
data = pd.DataFrame({
'DATE': pd.date_range('2019-01-01', freq='D', periods=m),
'REVENUE': np.random.randn(m),
'COST': np.random.randn(m),
}).melt('DATE', var_name='KEY', value_name='VALUE')
# Create a selection that chooses the nearest point & selects based on x-value
nearest = alt.selection(type='single', nearest=True, on='mouseover',
fields=['REVENUE'], empty='none')
# The basic line
line = alt.Chart(data).mark_bar(interpolate='basis').encode(
x='DATE:T',
y='VALUE:Q',
color='KEY:N'
).configure_bar(opacity=0.5)
line
您可以结合使用编码和构面来创建分组条形图,并且可以调整轴标题和刻度来自定义外观。这是一个示例(正如您在评论中提到的,在 Altair 中复制 https://vega.github.io/editor/#/examples/vega/grouped-bar-chart):
import altair as alt
import pandas as pd
data = pd.DataFrame([
{"category":"A", "position":0, "value":0.1},
{"category":"A", "position":1, "value":0.6},
{"category":"A", "position":2, "value":0.9},
{"category":"A", "position":3, "value":0.4},
{"category":"B", "position":0, "value":0.7},
{"category":"B", "position":1, "value":0.2},
{"category":"B", "position":2, "value":1.1},
{"category":"B", "position":3, "value":0.8},
{"category":"C", "position":0, "value":0.6},
{"category":"C", "position":1, "value":0.1},
{"category":"C", "position":2, "value":0.2},
{"category":"C", "position":3, "value":0.7}
])
text = alt.Chart(data).mark_text(dx=-10, color='white').encode(
x=alt.X('value:Q', title=None),
y=alt.Y('position:O', axis=None),
text='value:Q'
)
bars = text.mark_bar().encode(
color=alt.Color('position:O', legend=None, scale=alt.Scale(scheme='category20')),
)
(bars + text).facet(
row='category:N'
).configure_header(
title=None
)
原答案:
我无法准确地从你的问题中解析出你想要做什么(将来请考虑包含一个代码片段来展示你已经尝试过的内容并指出结果不充分的原因),但这里是包含这种形式数据的条形图示例,x 轴仅标有日期,工具提示和图例显示收入和成本:
import altair as alt
import pandas as pd
data = pd.DataFrame({
'DATE': pd.date_range('2019-01-01', freq='D', periods=4),
'REVENUE': [100, 200, 150, 50],
'COST': [150, 125, 75, 80],
}).melt('DATE', var_name='KEY', value_name='VALUE')
alt.Chart(data).mark_bar().encode(
x='yearmonthdate(DATE):O',
y='VALUE',
color='KEY',
tooltip=['KEY', 'VALUE'],
)