我希望有人能帮我把我现在的数据格式从宽格式转换成长格式。我使用的是Pandas 0.18.0,而且我似乎找不到适合我需要的堆栈溢出的任何其他解决方案。
任何帮助都将不胜感激!
我有50个步骤,每个步骤有两个类别(状态/时间),需要融化,这些类别在我的dataframe中交替。下面的是一个只有3组的示例,但是这种模式一直延续到50.。
状态可以是:是/否/南
时间可以是:时间戳/南
目前的数据:
cl_id cl_template_id status-1 time-1 status-2 time-2 status-3 time-3
0 18434 107 NaN NaN NaN NaN NaN NaN
1 18280 117 yes 2016-12-28T18:21:58+00:00 yes 2016-12-28T20:47:31+00:00 yes 2016-12-28T20:47:32+00:00
2 18356 413 yes 2017-01-11T19:23:10+00:00 yes 2017-01-11T19:23:11+00:00 yes 2017-01-11T19:23:11+00:00
3 18358 430 NaN NaN NaN NaN NaN NaN
4 18359 430 yes 2017-01-11T19:20:32+00:00 yes 2017-01-11T19:20:34+00:00 NaN NaN
.
.
.目标Dataframe:
cl_id cl_template_id step status time
18434 107 1 NaN NaN
18434 107 2 NaN NaN
18434 107 3 NaN NaN
18280 117 1 yes 2016-12-28T18:21:58+00:00
18280 117 2 yes 2016-12-28T20:47:31+00:00
18280 117 3 yes 2016-12-28T20:47:32+00:00
18356 413 1 yes 2017-01-11T19:23:10+00:00
18356 413 2 yes 2017-01-11T19:23:11+00:00
18356 413 3 yes 2017-01-11T19:23:11+00:00
.
.
.发布于 2017-09-22 20:01:53
希望这个答案能为这个问题提供一些见解。
首先,我将从您的dataframe重新创建一个示例:
# Make example dataframe
df = pd.DataFrame({'cl_id' : [18434, 18280, 18356, 18358, 18359],
'cl_template_id' : [107, 117, 413, 430, 430],
'status_1' : [np.NaN, 'yes', 'yes', np.NaN, 'yes'],
'time_1' : [np.NaN, '2016-12-28T18:21:58+00:00', '2017-01-11T19:23:10+00:00', np.NaN, '2017-01-11T19:20:32+00:00'],
'status_2' : [np.NaN, 'yes', 'yes', np.NaN, 'yes'],
'time_2' : [np.NaN, '2016-12-28T20:47:31+00:00', '2017-01-11T19:23:11+00:00', np.NaN, '2017-01-11T19:20:34+00:00'],
'status_3' : [np.NaN, 'yes', 'yes', np.NaN, np.NaN],
'time_3' : [np.NaN, '2016-12-28T20:47:32+00:00', '2017-01-11T19:23:11+00:00', np.NaN, np.NaN]})其次,将time_1,2,3转换为datetimes:
# Convert time_1,2,3 to datetime
df.loc[:, 'time_1'] = pd.to_datetime(df.loc[:, 'time_1'])
df.loc[:, 'time_2'] = pd.to_datetime(df.loc[:, 'time_2'])
df.loc[:, 'time_3'] = pd.to_datetime(df.loc[:, 'time_3'])第三,将dataframe分为两个部分,一个是状态,另一个是时间:
# Split df into a status, time dataframe
df_status = df.loc[:, :'status_3']
df_time = df.loc[:, ['cl_id', 'cl_template_id']].merge(df.loc[:, 'time_1':],
left_index = True,
right_index = True)第四,融化状态和时间数据:
# Melt status
df_status = df_status.melt(id_vars = ['cl_id',
'cl_template_id'],
value_vars = ['status_1',
'status_2',
'status_3'],
var_name = 'step',
value_name = 'status')
# Melt time
df_time = df_time.melt(id_vars = ['cl_id',
'cl_template_id'],
value_vars = ['time_1',
'time_2',
'time_3'],
var_name = 'step',
value_name = 'time')第五,清除状态和时间数据中的“步骤”列,只保留数字:
# Clean step in status, time
df_status.loc[:, 'step'] = df_status.loc[:, 'step'].str.partition('_')[2]
df_time.loc[:, 'step'] = df_time.loc[:, 'step'].str.partition('_')[2]第六,将状态和时间数据重新合并到最后的dataframe中:
# Merge status, time back together on cl_id, cl_template_id
final = df_status.merge(df_time,
how = 'inner',
on = ['cl_id',
'cl_template_id',
'step']).sort_values(by = ['cl_template_id',
'cl_id']).reset_index(drop = True)瞧!你想要的答案是:

发布于 2020-02-06 09:52:33
但是我也面临着同样的问题,我认为特德·彼得鲁的这个答案可以很好地帮助你:熊猫将几组列按名称融化成多个目标列。
pd.wide_to_long(df, stubnames, i, j, sep, suffix) 简而言之:龙()函数允许您指定要取消枢轴的各个列之间的公共组件。
例如,我的dataframe类似于您的数据,如下所示:

pd.melt和pd.unstack使您接近,但不允许您按照它们的公共分母来锁定这些增量列组。
https://stackoverflow.com/questions/42708176
复制相似问题