整数的 Pandas 多重索引如何转换为日期时间索引?

3

我有一个数据框,如下所示,其中包含了年份中的月份和日期等整数的多重索引,以及这些日期的最高温度和最低温度记录。

df

          Min Temp  Max Temp
Date Date                    
1    1          -88       139
     2         -115       150
     3         -110       139
     4          -81       156
     5          -80       172
...             ...       ...
12   2          -94       156
     3          -97       172
     4         -120       156
     5         -124       144
     6         -161       130
     7         -167       135
     8         -141       167
     9         -135       178
     10        -106       194
     11        -106       161
     12         -94       144
     13         -92       133
     14        -149       117
     15        -158       117
     16        -119       122
     17        -111       160
     18        -142       133
     19        -185       130
     20        -190       161
     21        -167       161
     22         -98       150
     23        -162       139
     24         -90       183
     25        -125       183
     26        -119       144
     27         -76       130
     28         -81       134
     29        -117       113
     30        -127       106
     31        -111       122

我应该如何将这个多层次索引转换为单一的日期时间类型的索引?我正在寻求类似于以下的转换:
1 1 ---> January 1
1 2 ---> January 2
...
12 31 ---> December 31

1
你想要哪一年? - ALollz
我建议使用 reset_index(),然后组合生成的列以创建新列,将其转换为日期时间并设置为索引。 - rahlf23
@ALollz,这些是某个地区大约10年期间的最低和最高温度,因此数据没有与单个年份相关联。 - bwrabbit
1
一个 datetime 至少需要年、月和日来定义。如果你需要使用 datetime,你可以选择一些虚拟的年份,比如 1900 年。 - ALollz
2个回答

3

以您的数据框顶部为例:

>>> df
           Min Temp  Max Temp
Date Date                    
1    1          -88       139
     2         -115       150
     3         -110       139
     4          -81       156
     5          -80       172

使用pd.to_datetime函数对您的MultiIndex的各个级别进行操作,然后使用strftime函数设置您想要的格式:

df.index = pd.to_datetime(df.index.get_level_values(0).astype(str) + '-' +
               df.index.get_level_values(1).astype(str),
               format='%m-%d').strftime('%B %d')

>>> df
            Min Temp  Max Temp
January 01       -88       139
January 02      -115       150
January 03      -110       139
January 04       -81       156
January 05       -80       172

然而,由于这是一个格式化的字符串,它将不再是日期时间格式。如果您想要它成为日期时间格式,您需要包含年份。您可以省略 strftime,它将使用默认值 1900

df.index = pd.to_datetime(df.index.get_level_values(0).astype(str) + '-' +
               df.index.get_level_values(1).astype(str),
               format='%m-%d')

>>> df
            Min Temp  Max Temp
1900-01-01       -88       139
1900-01-02      -115       150
1900-01-03      -110       139
1900-01-04       -81       156
1900-01-05       -80       172

1

让我们来看一下这个示例数据框:

import pandas as pd
import numpy as np

arrays = [[1, 1, 1, 1, 2, 2, 2, 2], [28, 29, 30, 31 , 1, 2, 3, 4]]

index = pd.MultiIndex.from_arrays(arrays, names=('Month', 'Day'))

df = pd.DataFrame(np.random.randn(8,2), index=index)

产生:

   Month  Day         0         1
0      1   28 -0.295065 -0.843433
1      1   29  0.367759  0.837147
2      1   30  0.051956  0.430499
3      1   31  1.917990  1.066545
4      2    1  1.345338 -0.600304
5      2    2 -0.475890  0.763301
6      2    3  0.560985  1.747668
7      2    4  0.377741 -0.310094

只需使用reset_index(),组合列并转换为日期时间:

new = df.reset_index()

new['Date'] = pd.to_datetime(new['Month'].astype(str) + '/' + new['Day'].astype(str), format='%m/%d')

产生:

   Month  Day         0         1       Date
0      1   28 -0.295065 -0.843433 1900-01-28
1      1   29  0.367759  0.837147 1900-01-29
2      1   30  0.051956  0.430499 1900-01-30
3      1   31  1.917990  1.066545 1900-01-31
4      2    1  1.345338 -0.600304 1900-02-01
5      2    2 -0.475890  0.763301 1900-02-02
6      2    3  0.560985  1.747668 1900-02-03
7      2    4  0.377741 -0.310094 1900-02-04

最后,使用 set_index()drop() 函数来操作列:
new = new.set_index('Date').drop(['Month','Day'], axis=1)

产生:
                   0         1
Date                          
1900-01-28  0.503419 -1.197496
1900-01-29 -0.059114  0.552766
1900-01-30  0.365710 -0.079030
1900-01-31 -2.782296  1.027040
1900-02-01  1.343155 -0.846419
1900-02-02  1.334560  0.392820
1900-02-03  0.537082  1.486579
1900-02-04  0.506200  0.138864

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接