Pandas: 使用groupby统计日期之间的差异
Pandas: use groupby to count difference between dates
我有 df:
i,Unnamed,ID,url,used_at,active_seconds,domain,subdomain,search_engine,search_term,diff_time,period
0,322015,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/antoninaribina,2015-12-31 09:16:05,35,vk.com,vk.com,None,None,,1
1,838267,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/feed,2015-12-31 09:16:38,54,vk.com,vk.com,None,None,33.0,1
2,838271,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/feed?section=photos,2015-12-31 09:17:32,34,vk.com,vk.com,None,None,54.0,1
3,322026,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/feed?section=photos&z=photo143297356_397216312%2Ffeed1_143297356_1451504298,2015-12-31 09:18:06,4,vk.com,vk.com,None,None,34.0,1
4,838275,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/feed?section=photos,2015-12-31 09:18:10,4,vk.com,vk.com,None,None,4.0,1
5,322028,7602962fb83ac2e2a0cb44158ca88464,vk.com/feed?section=comments,2015-12-29 09:18:14,8,vk.com,vk.com,None,None,4.0,1
6,322029,7602962fb83ac2e2a0cb44158ca88464,megarand.ru/contest/121070,2015-12-30 09:18:22,16,megarand.ru,megarand.ru,None,None,8.0,1
7,1870917,7602962fb83ac2e2a0cb44158ca88464,vk.com/feed?section=comments,2015-12-31 09:18:38,6,vk.com,vk.com,None,None,16.0,1
我需要为每个 ID
打印第一个日期和最后一个日期之间的差异。我该怎么做?
我尝试使用 df.groupby('ID')['used_at'].diff().dt.seconds
但它打印出每 2 个字符串之间的差异
我认为你需要 groupby
与 first
and last
不同:
g = df.groupby('ID')['used_at']
print (g.first() - g.last())
ID
0120bc30e78ba5582617a9f3d6dfd8ca -1 days +23:57:55
7602962fb83ac2e2a0cb44158ca88464 -3 days +23:59:36
Name: used_at, dtype: timedelta64[ns]
或申请iloc
:
print (df.groupby('ID')['used_at'].apply(lambda g: g.iloc[0] - g.iloc[-1]))
ID
0120bc30e78ba5582617a9f3d6dfd8ca -1 days +23:57:55
7602962fb83ac2e2a0cb44158ca88464 -3 days +23:59:36
Name: used_at, dtype: timedelta64[ns]
将 timedelta
转换为 seconds
:
g = df.groupby('ID')['used_at']
print ((g.first() - g.last()).dt.seconds)
ID
0120bc30e78ba5582617a9f3d6dfd8ca 86275
7602962fb83ac2e2a0cb44158ca88464 86376
Name: used_at, dtype: int64
print (df.groupby('ID')['used_at'].apply(lambda g: g.iloc[0] - g.iloc[-1]).dt.seconds)
ID
0120bc30e78ba5582617a9f3d6dfd8ca 86275
7602962fb83ac2e2a0cb44158ca88464 86376
Name: used_at, dtype: int64
感谢 juanpa.arrivillaga
:
如果日期时间是排序的,你可以使用:
df.groupby('ID').used_at.min() - df.groupby('ID').used_at.max()
时间:
In [216]: %timeit (a(df))
The slowest run took 4.30 times longer than the fastest. This could mean that an intermediate result is being cached.
1000 loops, best of 3: 1.78 ms per loop
In [217]: %timeit (b(df))
1000 loops, best of 3: 1.8 ms per loop
In [218]: %timeit (df.groupby('ID')['used_at'].apply(lambda g: g.iloc[0] - g.iloc[-1]).dt.seconds)
1000 loops, best of 3: 1.53 ms per loop
In [219]: %timeit (df.groupby('ID').agg(['first','last']).apply( lambda r: r['used_at','first'] - r['used_at','last'], axis=1).dt.seconds)
100 loops, best of 3: 14.4 ms per loop
时间代码:
df = pd.concat([df]*1000).reset_index(drop=True)
def a(df):
g = df.groupby('ID')['used_at']
return ((g.first() - g.last()).dt.seconds)
def b(df):
g = df.groupby('ID')['used_at']
return ((g.min() - g.max()).dt.seconds)
有一条线。
df.groupby('ID').agg(['first','last']).apply( lambda r: r['used_at','last'] - r['used_at','first'], axis=1)
首先按列分组 ID
,然后对每组取第一个和最后一个元素并计算差值 last - first
。
我有 df:
i,Unnamed,ID,url,used_at,active_seconds,domain,subdomain,search_engine,search_term,diff_time,period
0,322015,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/antoninaribina,2015-12-31 09:16:05,35,vk.com,vk.com,None,None,,1
1,838267,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/feed,2015-12-31 09:16:38,54,vk.com,vk.com,None,None,33.0,1
2,838271,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/feed?section=photos,2015-12-31 09:17:32,34,vk.com,vk.com,None,None,54.0,1
3,322026,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/feed?section=photos&z=photo143297356_397216312%2Ffeed1_143297356_1451504298,2015-12-31 09:18:06,4,vk.com,vk.com,None,None,34.0,1
4,838275,0120bc30e78ba5582617a9f3d6dfd8ca,vk.com/feed?section=photos,2015-12-31 09:18:10,4,vk.com,vk.com,None,None,4.0,1
5,322028,7602962fb83ac2e2a0cb44158ca88464,vk.com/feed?section=comments,2015-12-29 09:18:14,8,vk.com,vk.com,None,None,4.0,1
6,322029,7602962fb83ac2e2a0cb44158ca88464,megarand.ru/contest/121070,2015-12-30 09:18:22,16,megarand.ru,megarand.ru,None,None,8.0,1
7,1870917,7602962fb83ac2e2a0cb44158ca88464,vk.com/feed?section=comments,2015-12-31 09:18:38,6,vk.com,vk.com,None,None,16.0,1
我需要为每个 ID
打印第一个日期和最后一个日期之间的差异。我该怎么做?
我尝试使用 df.groupby('ID')['used_at'].diff().dt.seconds
但它打印出每 2 个字符串之间的差异
我认为你需要 groupby
与 first
and last
不同:
g = df.groupby('ID')['used_at']
print (g.first() - g.last())
ID
0120bc30e78ba5582617a9f3d6dfd8ca -1 days +23:57:55
7602962fb83ac2e2a0cb44158ca88464 -3 days +23:59:36
Name: used_at, dtype: timedelta64[ns]
或申请iloc
:
print (df.groupby('ID')['used_at'].apply(lambda g: g.iloc[0] - g.iloc[-1]))
ID
0120bc30e78ba5582617a9f3d6dfd8ca -1 days +23:57:55
7602962fb83ac2e2a0cb44158ca88464 -3 days +23:59:36
Name: used_at, dtype: timedelta64[ns]
将 timedelta
转换为 seconds
:
g = df.groupby('ID')['used_at']
print ((g.first() - g.last()).dt.seconds)
ID
0120bc30e78ba5582617a9f3d6dfd8ca 86275
7602962fb83ac2e2a0cb44158ca88464 86376
Name: used_at, dtype: int64
print (df.groupby('ID')['used_at'].apply(lambda g: g.iloc[0] - g.iloc[-1]).dt.seconds)
ID
0120bc30e78ba5582617a9f3d6dfd8ca 86275
7602962fb83ac2e2a0cb44158ca88464 86376
Name: used_at, dtype: int64
感谢 juanpa.arrivillaga
如果日期时间是排序的,你可以使用:
df.groupby('ID').used_at.min() - df.groupby('ID').used_at.max()
时间:
In [216]: %timeit (a(df))
The slowest run took 4.30 times longer than the fastest. This could mean that an intermediate result is being cached.
1000 loops, best of 3: 1.78 ms per loop
In [217]: %timeit (b(df))
1000 loops, best of 3: 1.8 ms per loop
In [218]: %timeit (df.groupby('ID')['used_at'].apply(lambda g: g.iloc[0] - g.iloc[-1]).dt.seconds)
1000 loops, best of 3: 1.53 ms per loop
In [219]: %timeit (df.groupby('ID').agg(['first','last']).apply( lambda r: r['used_at','first'] - r['used_at','last'], axis=1).dt.seconds)
100 loops, best of 3: 14.4 ms per loop
时间代码:
df = pd.concat([df]*1000).reset_index(drop=True)
def a(df):
g = df.groupby('ID')['used_at']
return ((g.first() - g.last()).dt.seconds)
def b(df):
g = df.groupby('ID')['used_at']
return ((g.min() - g.max()).dt.seconds)
有一条线。
df.groupby('ID').agg(['first','last']).apply( lambda r: r['used_at','last'] - r['used_at','first'], axis=1)
首先按列分组 ID
,然后对每组取第一个和最后一个元素并计算差值 last - first
。