具有多个系列的 Seaborn 时间序列图

Posted

技术标签:

【中文标题】具有多个系列的 Seaborn 时间序列图【英文标题】:Seaborn timeseries plot with multiple series 【发布时间】:2016-09-07 04:32:33 【问题描述】:

我正在尝试从具有多个系列的数据框中使用 seaborn 制作时间序列图。

来自这篇文章: seaborn time series from pandas dataframe

我认为 tsplot 不会起作用,因为它旨在绘制不确定性。

那么还有另一种适用于具有多个系列的折线图的 Seaborn 方法吗?

我的数据框如下所示:

print(df.info())
print(df.describe())
print(df.values)
print(df.index)

输出:

<class 'pandas.core.frame.DataFrame'>
DatetimeIndex: 253 entries, 2013-01-03 to 2014-01-03
Data columns (total 5 columns):
Equity(24 [AAPL])      253 non-null float64
Equity(3766 [IBM])     253 non-null float64
Equity(5061 [MSFT])    253 non-null float64
Equity(6683 [SBUX])    253 non-null float64
Equity(8554 [SPY])     253 non-null float64
dtypes: float64(5)
memory usage: 11.9 KB
None
       Equity(24 [AAPL])  Equity(3766 [IBM])  Equity(5061 [MSFT])  \
count         253.000000          253.000000           253.000000   
mean           67.560593          194.075383            32.547436   
std             6.435356           11.175226             3.457613   
min            55.811000          172.820000            26.480000   
25%            62.538000          184.690000            28.680000   
50%            65.877000          193.880000            33.030000   
75%            72.299000          203.490000            34.990000   
max            81.463000          215.780000            38.970000   

       Equity(6683 [SBUX])  Equity(8554 [SPY])  
count           253.000000          253.000000  
mean             33.773277          164.690180  
std               4.597291           10.038221  
min              26.610000          145.540000  
25%              29.085000          156.130000  
50%              33.650000          165.310000  
75%              38.280000          170.310000  
max              40.995000          184.560000  
[[  77.484  195.24    27.28    27.685  145.77 ]
 [  75.289  193.989   26.76    27.85   146.38 ]
 [  74.854  193.2     26.71    27.875  145.965]
 ..., 
 [  80.167  187.51    37.43    39.195  184.56 ]
 [  79.034  185.52    37.145   38.595  182.95 ]
 [  77.284  186.66    36.92    38.475  182.8  ]]
DatetimeIndex(['2013-01-03', '2013-01-04', '2013-01-07', '2013-01-08',
               '2013-01-09', '2013-01-10', '2013-01-11', '2013-01-14',
               '2013-01-15', '2013-01-16', 
               ...
               '2013-12-19', '2013-12-20', '2013-12-23', '2013-12-24',
               '2013-12-26', '2013-12-27', '2013-12-30', '2013-12-31',
               '2014-01-02', '2014-01-03'],
              dtype='datetime64[ns]', length=253, freq=None, tz='UTC')

这行得通(但我想用 Seaborn 弄脏我的手):

df.plot()

输出:

感谢您的宝贵时间!

更新1:

df.to_dict() 返回: https://gist.github.com/anonymous/2bdc1ce0f9d0b6ccd6675ab4f7313a5f

更新2:

使用@knagaev 示例代码,我将其缩小到这种差异:

当前数据帧(print(current_df) 的输出):

                           Equity(24 [AAPL])  Equity(3766 [IBM])  \
2013-01-03 00:00:00+00:00             77.484            195.2400   
2013-01-04 00:00:00+00:00             75.289            193.9890   
2013-01-07 00:00:00+00:00             74.854            193.2000   
2013-01-08 00:00:00+00:00             75.029            192.8200   
2013-01-09 00:00:00+00:00             73.873            192.3800   

所需的数据帧(print(desired_df) 的输出):

           Date Company       Kind            Price
0    2014-01-02     IBM       Open       187.210007
1    2014-01-02     IBM       High       187.399994
2    2014-01-02     IBM        Low       185.199997
3    2014-01-02     IBM      Close       185.529999
4    2014-01-02     IBM     Volume   4546500.000000
5    2014-01-02     IBM  Adj Close       171.971090
6    2014-01-02    MSFT       Open        37.349998
7    2014-01-02    MSFT       High        37.400002
8    2014-01-02    MSFT        Low        37.099998
9    2014-01-02    MSFT      Close        37.160000
10   2014-01-02    MSFT     Volume  30632200.000000
11   2014-01-02    MSFT  Adj Close        34.960000
12   2014-01-02    ORCL       Open        37.779999
13   2014-01-02    ORCL       High        38.029999
14   2014-01-02    ORCL        Low        37.549999
15   2014-01-02    ORCL      Close        37.840000
16   2014-01-02    ORCL     Volume  18162100.000000

current_df 重组为desired_df 的最佳方法是什么?

更新 3: 我终于在@knagaev 的帮助下让它工作了:

我必须添加一个虚拟列以及优化索引:

df['Datetime'] = df.index
melted_df = pd.melt(df, id_vars='Datetime', var_name='Security', value_name='Price')
melted_df['Dummy'] = 0

sns.tsplot(melted_df, time='Datetime', unit='Dummy', condition='Security', value='Price', ax=ax)

产生:

【问题讨论】:

seaborn 通常不会复制 matplotlib 或 pandas 中可用的功能。你有什么具体的尝试吗? 您能否发布df.to_csv()df.to_dict() 的输出 - 这样我们就可以轻松地重新创建您的DF? Seaborn 是一个用于绘制特殊统计数据的高级库——统计工具输出的可视化。使用它来绘制简单的折线图,例如使用一些 C++ 高级库 (STL) 进行指针操作。 @AL 在您的示例中使用 tsplot 存在问题 - tsplot(与 seaborn 中的其他图表一样)预计时间轴的一个点有多个值。它聚合它们,这就是为什么对于每个“条件”,您都会得到一条带有标准错误的线条和一条条纹。但是您对数据框中的每个时间点都有唯一的价值。好吗? 请看我更新的答案 - 我使用虚拟列来绘制“单值”数据框。 【参考方案1】:

您可以尝试使用tsplot 弄脏手。

您将绘制带有标准误差(“统计加法”)的折线图

我试图模拟您的数据集。所以这里是结果

import pandas.io.data as web
from datetime import datetime
import seaborn as sns

stocks = ['ORCL', 'TSLA', 'IBM','YELP', 'MSFT']
start = datetime(2014,1,1)
end = datetime(2014,3,28)    
f = web.DataReader(stocks, 'yahoo',start,end)

df = pd.DataFrame(f.to_frame().stack()).reset_index()
df.columns = ['Date', 'Company', 'Kind', 'Price']

sns.tsplot(df, time='Date', unit='Kind', condition='Company', value='Price')

顺便说一下,这个样本非常具有模仿性。参数“unit”是“data DataFrame 中标识采样单元(例如主题、神经元等)的字段。错误表示将在每次/条件观察时在单元上折叠。”(来自文档)。所以我使用“种类”字段进行说明。

好的,我为您的数据框做了一个示例。 它有“噪音清理”的虚拟字段:)

import pandas.io.data as web
from datetime import datetime
import seaborn as sns

stocks = ['ORCL', 'TSLA', 'IBM','YELP', 'MSFT']
start = datetime(2010,1,1)
end = datetime(2015,12,31)    
f = web.DataReader(stocks, 'yahoo',start,end)

df = pd.DataFrame(f.to_frame().stack()).reset_index()
df.columns = ['Date', 'Company', 'Kind', 'Price']

df_open = df[df['Kind'] == 'Open'].copy()
df_open['Dummy'] = 0

sns.tsplot(df_open, time='Date', unit='Dummy', condition='Company', value='Price')

附:感谢@VanPeer - 现在你可以使用seaborn.lineplot 来解决这个问题

【讨论】:

链接已弃用 @VanPeer 是的,你是对的,tsplot 已被弃用。取而代之的是 seaborn.lineplot seaborn.pydata.org/examples/errorband_lineplots.html

以上是关于具有多个系列的 Seaborn 时间序列图的主要内容,如果未能解决你的问题,请参考以下文章

具有连续色调的 Seaborn 配对图?

seaborn distplot / displot 具有多个分布

使用单个数据帧的多个标签调整图例 Seaborn 联合图

具有不同长度数组的seaborn联合图

如何将 pandas 系列转换为 seaborn 条形图

如何缩放具有不同频率的多个KDE图?