旋转Pandas数据帧



我有下面的Pandas DataFrame,有50列,它包括一些精选股票的每日收盘现货价格和期权价格,总共25只股票,但我在这里只显示了3只。这里显示的价格只是一个例子:

date           tsla_spot   tsla_options aapl_spot  aapl_options msft_spot  msft_options 
2020-01-01       350            23.02      257.21      3.45        170.32      3.56
2020-01-02       345.64         21.32      260.10      3.79        123.45      43.21
2020-01-03       345.12         20.43      262.12      3.90        123.54      45.32

我想有以下熊猫数据帧,但不知道如何。。。相反,它被称为pivot吗?

date          stock    spot    options
2020-01-01     tsla     350      23.02
2020-01-01     aapl     257.21   3.79
2020-01-01     msft     170.32   3.56
2020-01-02     tsla     345.64   21.32
2020-01-02     aapl     260.10   3.79
2020-01-02     msft     123.45    43.21

谢谢你!

您可以通过首先重新组织列来使用pd.wide_to_long

pattern = r"(?P<first>w+)_(?P<last>w+)"
repl = lambda m: f"{m.group('last')}_{m.group('first')}"
df.columns = df.columns.str.replace(pattern, repl)
df.columns
Index(['date', 'spot_tsla', 'options_tsla', 'spot_aapl', 'options_aapl',
'spot_msft', 'options_msft'],
dtype='object')

现在,应用wide_to_long函数:

pd.wide_to_long(df, 
stubnames=["spot", "options"], 
i="date", 
j="stock", 
sep="_", 
suffix=".+")
spot   options
date       stock        
2020-01-01  tsla    350.00  23.02
2020-01-02  tsla    345.64  21.32
2020-01-03  tsla    345.12  20.43
2020-01-01  aapl    257.21  3.45
2020-01-02  aapl    260.10  3.79
2020-01-03  aapl    262.12  3.90
2020-01-01  msft    170.32  3.56
2020-01-02  msft    123.45  43.21
2020-01-03  msft    123.54  45.32

另一个选项是使用pyjanitor:中的pivot_langer函数

import janitor
df.pivot_longer(index="date", 
names_to=("stock", ".value"), 
names_sep="_")

date    stock        spot   options
0   2020-01-01  tsla    350.00  23.02
1   2020-01-01  aapl    257.21  3.45
2   2020-01-01  msft    170.32  3.56
3   2020-01-02  tsla    345.64  21.32
4   2020-01-02  aapl    260.10  3.79
5   2020-01-02  msft    123.45  43.21
6   2020-01-03  tsla    345.12  20.43
7   2020-01-03  aapl    262.12  3.90
8   2020-01-03  msft    123.54  45.32

.value告诉函数将spotoptions设为新的列名,其余列变为stock列中的值。

将没有分隔符的列转换为索引,为MultiIndex拆分列名,并通过DataFrame.stack使用DataFrame.rename_axis对新列名进行整形:

df = df.set_index('date')
df.columns = df.columns.str.split('_', expand=True)
df = df.stack(0).rename_axis(['date', 'stock']).reset_index()
print (df)
date stock  options    spot
0  2020-01-01  aapl     3.45  257.21
1  2020-01-01  msft     3.56  170.32
2  2020-01-01  tsla    23.02  350.00
3  2020-01-02  aapl     3.79  260.10
4  2020-01-02  msft    43.21  123.45
5  2020-01-02  tsla    21.32  345.64
6  2020-01-03  aapl     3.90  262.12
7  2020-01-03  msft    45.32  123.54
8  2020-01-03  tsla    20.43  345.12

最新更新