当前位置: 首页 > 知识库问答 >
问题:

通过groupby确定开始/结束日期

皮献
2023-03-14

我试图找到一种干净的Python/Pandas方法来获取以下数据帧:

ID  Date_Field Category 
12345 01/01/12 AAAA
12345 01/02/12 AAAA
12345 01/03/12 AAAA
12345 01/04/12 BBBB
12345 01/05/12 BBBB
12345 01/06/12 BBBB
2468  01/01/12 AAAA
2468  01/02/12 AAAA
2468  01/03/12 AAAA
2468  01/04/12 BBBB
2468  01/05/12 BBBB
2468  01/06/12 BBBB
2468  01/07/12 BBBB
2468  01/08/12 CCCC
2468  01/09/12 CCCC
2468  01/10/12 AAAA
2468  01/11/12 AAAA

并将其转换为类似于此的数据帧,即每个ID/类别都有开始/结束日期,但需要注意的是,如果在以下两个日期之间存在日期间隔,则ID/类别组合可能会出现多次:

ID  Start_Date End_Date Category
12345 01/01/12 01/03/12 AAAA
12345 01/04/12 01/06/12 BBBB
2468  01/01/12 01/03/12 AAAA
2468  01/10/12 01/11/12 AAAA
2468  01/04/12 01/07/12 BBBB
2468  01/08/12 01/09/12 CCCC

我知道我可以通过迭代和与前面的行值进行比较来实现,但我感觉有一种更干净的方法。

共有1个答案

徐鸿文
2023-03-14

您可以执行groupby。如果只需要一列,可以执行以下操作:

>>> df.groupby(['ID','Category']).min()

               Date_Field
ID    Category           
2468  AAAA       01/01/12
      BBBB       01/04/12
      CCCC       01/08/12
12345 AAAA       01/01/12
      BBBB       01/04/12

要做到最大,你可以这样回答:

>>> df.groupby(['ID','Category']).agg({'Date_Field' : [min, max]})

               Date_Field          
                      min       max
ID    Category                     
2468  AAAA       01/01/12  01/11/12
      BBBB       01/04/12  01/07/12
      CCCC       01/08/12  01/09/12
12345 AAAA       01/01/12  01/03/12
      BBBB       01/04/12  01/06/12

编辑:

group pby会生成一个以分组列为索引的DataFrame,以禁用这个addas_index=False

>>> df.groupby(['ID','Category'], as_index=False).agg({'Date_Field' : [min, max]})

      ID Category Date_Field          
                         min       max
0   2468     AAAA   01/01/12  01/11/12
1   2468     BBBB   01/04/12  01/07/12
2   2468     CCCC   01/08/12  01/09/12
3  12345     AAAA   01/01/12  01/03/12
4  12345     BBBB   01/04/12  01/06/12

编辑2:

要分离具有相同ID和类别的数据的不同时间间隔,我们必须添加一个新类别:

df['Cat2']=0
for i in range(2,len(df)):
   if df['Category'].iloc[i]==df['Category'][i-1]:
     df['Cat2'].iloc[i]=df['Cat2'].iloc[i-1]
   else:
     df['Cat2'].iloc[i]=df['Cat2'].iloc[i-1]+1

这个for循环创建一个新的Cat2列,如果前一行(i-1)具有相同的类别,则该列将具有相同的值,否则将创建一个新值(前1)。注意,这个方法纯粹取决于数据的顺序!现在我们可以将其添加Groupby类别中:

 >>> df.groupby(['ID','Category','Cat2'], as_index=False).agg({'Date_Field' : [min, max]})

      ID Category Cat2 Date_Field          
                              min       max
0   2468     AAAA    2   01/01/12  01/03/12
1   2468     AAAA    5   01/10/12  01/11/12
2   2468     BBBB    3   01/04/12  01/07/12
3   2468     CCCC    4   01/08/12  01/09/12
4  12345     AAAA    0   01/01/12  01/03/12
5  12345     BBBB    1   01/04/12  01/06/12
 类似资料:
  • 问题内容: 好吧,假设我有一个看起来像这样的表: 任何人都有关于如何查询它的想法,因此数据看起来像 问题答案: 我不会将ID放在这里,因为我认为它与查询无关。如果您愿意,请稍后再说。这是一个MSSQL查询。 可以很容易地将其翻译为其他数据库类型。

  • 问题内容: 如果可能的话,在以下情况下,我希望使用joda或非joda解决方案 假设我的一周从2012年5月2日开始,给定的当前日期为02/22/2011。我需要计算给定当前日期的星期开始和结束日期。因此,我的解决方案的星期应该从02/19开始,而星期在02/25结束。为简单起见,我将我的工作日设置为02/05/2011,但是可能是任何一天,我的工作日始终为7天。 我现有的代码如下,但似乎无法按预

  • 问题内容: 我需要Java中本月的开始日期和结束日期。当JSP页面加载了当前月份时,它将自动计算该月份的开始和结束日期。它应该与年份和月份无关。也就是说某个月有31天或30天或28天。这也应该满足a年。你能帮我吗? 例如,如果我在列表框中选择“五月”,则需要开始日期为1,结束日期为31。 问题答案: 你去了: PS:类只是两个值的一对。

  • 这(我希望)是一个基本问题。我没有在fullcalendar中看到日历事件,我认为问题是我尝试用于开始/结束事件的日期格式。我试图通过加载JSON事件来设置一个基本日历。下面是我的JSON输出(为了不占用太多空间,修剪为一个事件): 我的javascript如下所示: 再说一遍,非常基本。我确定事件未出现的问题是由于我使用的日期格式造成的,但我不确定如何告诉fullCalendar使用格式来使用m

  • 7. 直播开始/结束,/录制结束回调通知 7.1. 功能 通知客户直播已开始/结束,此接口为我方调用客户的接口,告知客户直播过程已开始(或结束) 7.2. 地址 由客户提供 7.3. 请求参数 直播结束参数: 必须有的参数: 流名,liveId(场次号),开始时间,结束时间 其它参数:推流端IP,推流URL 录制结束参数: 必须有的参数: 流名,liveId(场次号),开始时间,结束时间,状态(录