将Pandas数据帧重塑为系列元素

2024-04-29 16:18:35 发布

您现在位置:Python中文网/ 问答频道 /正文

我对一个以日期作为索引值,以时间作为列值的pandas数据帧有问题,例如

states = pd.DataFrame([[1, 2], [4, 5]], columns=(
'00:00', '01:00'), index = ['2007-01-01', '2007-01-02'])

结果如下:

^{pr2}$

我现在想把它转换成一个系列,看起来像:

2007-01-01 00:00 1
2007-01-01 01:00 2
2007-01-02 00:00 4
2007-01-02 01:00 5

以整个时间戳作为索引。我试着把这个系列

blib = states.iloc[0]
blub = states.iloc[1]
pd.concat([blib, blub])

但是我会丢失日期信息。在


Tags: columns数据dataframepandasindex时间pd我会
3条回答

您可以通过执行开始的concat并将其扩展到另一个轴来实现这一点。通过从这些系列创建两个数据帧,可以将它们重新合并在一起并创建所需的索引:

blib = states.iloc[0]
blub = states.iloc[1]

times_df = pd.DataFrame(pd.concat([blib, blub]), columns=['value'])
times_df.reset_index(inplace=True)
# Renaming index so that there aren't two 'index' columns after merge
times_df.rename(columns={'index': 'time'}, inplace=True)

a = states['00:00']
b = states['01:00']

dates_df = pd.DataFrame(pd.concat([a, b]), columns=['value'])
dates_df.reset_index(inplace=True)
dates_df.rename(columns={'index': 'date'}, inplace=True)

# Merging gives the four rows you want but still need to create index
merged = pd.merge(times_df, dates_df, on='value')

merged['datetime'] = pd.to_datetime(merged['date'] + ' ' + merged['time'])
merged.drop(['date', 'time'], axis=1, inplace=True)

merged.set_index('datetime', drop=True, inplace=True)

result = merged['value']

结果输出:

^{pr2}$

如果您希望将索引作为字符串,请将merged['datetime'] = ...行改为:

merged['datetime'] = merged['date'] + ' ' + merged['time']

结果将完全符合您的要求:

datetime
2007-01-01 00:00    1
2007-01-01 01:00    2
2007-01-02 00:00    4
2007-01-02 01:00    5
Name: value, dtype: int64

编辑:我意识到这不是很有效,多索引方法可能更有前途。在

您可以使用stack()

In [1]: states.stack()
Out[1]:
2007-01-01  00:00    1
            01:00    2
2007-01-02  00:00    4
            01:00    5
dtype: int64

In [2]: type(states.stack())
Out[2]: pandas.core.series.Series

farhawa的建议有助于将多个索引统一到一个单独的索引中(这在我的例子中是有意义的,因为索引是一个日期时间,而索引并不是真正的多维的。大多数时候,多重索引可能是更好的解决方案)。在

我们使用法哈瓦的建议

pp = states.stack()

得到一个多重索引

^{pr2}$

将它们组合到一个新索引中并重新分配可以解决以下问题:

newIndex = [pp.index.levels[0][l0] + ' ' + pp.index.levels[1][l1]
                for l0, l1 in zip(pp.index.labels[0], blub.index.labels[1])]
newIndex = pd.DatetimeIndex(newIndex) 
pp = pd.Series(pp.values,index = newIndex)

重新创作这个系列可能不是最有效的方法,因此我很乐意为您提供更好的建议。在

相关问题 更多 >