2017-10-11 127 views
0

我有一个包含类似这样的事件数据框:拆分数据帧由行日期时间在大熊猫

location start_time end_time  some_value1 some_value2 
LECP  00:00  01:30  25   nice info 
LECP  02:00  04:00  10   other info 
LECS  02:00  03:00   5   lorem 
LIPM  02:55  03:15   9   ipsum 

,我想,这样我得到的最大1 hour间隔,例如分裂行如果一个事件的持续时间为01:30,我想获得一行长度为01:00,另一个为00:30。如果一个事件的长度为02:30,我想得到三行。如果一个事件持续一个小时或更少,它应该保持一行。像这样:

location start_time end_time some_value1 some_value2 
LECP  00:00  01:00  25   nice info 
LECP  01:00  01:30  25   nice info 

LECP  02:00  03:00  10   other info 
LECP  03:00  04:00  10   other info 

LECS  02:00  03:00  5   lorem 
LIPM  02:55  03:15  9   ipsum 

如果余数在开始或结束时无关紧要。如果持续时间平均分配给行,则无关紧要,只要没有行的持续时间大于1小时即可。

我试过的东西: - 通过Time Series/Date functionality阅读并不理解任何东西 - 正在搜索StackOverflow。

+0

这是因为这些是独立事件。一些事件可能发生在相同或不同的地方,在相同或不同的时间 – Ulu83

+0

呃......对不起。我的问题是在你的预期结果中,如果第二条记录从01:00开始而不是00:00? –

+0

我的不好。是的,你的解释是对的。编辑OP。 – Ulu83

回答

0

我改编this答案实施每小时而不是每日拆分。这段代码在WHIL循环中工作,所以只要有持续时间> 1小时的行,它就会重新迭代。

mytimedelta = pd.Timedelta('1 hour') 

#create boolean mask 
split_rows = (dfob['duration'] > mytimedelta)  

while split_rows.any(): 
    #get new rows to append and adjust start time to 1 hour later. 
    new_rows = dfob[split_rows].copy() 
    new_rows['start'] = new_rows['start'] + mytimedelta 

    #update the end time of old rows 
    dfob.loc[split_rows, 'end'] = dfob.loc[split_rows, 'start'] + \ 
     pd.DateOffset(hours=1, seconds=-1) 
    dfob = dfob.append(new_rows) 

    #update the duration of all rows 
    dfob['duration'] = dfob['end'] - dfob['start'] 

    #create an updated boolean mask 
    split_rows = (dfob['duration'] > mytimedelta) 

#when job is done: 
dfob.sort_index().reset_index(drop=True) 
dfob['duration'] = dfob['end'] - dfob['start']