【问题标题】:group by id1 and id2 and apply a function using another dataframe and dates按 id1 和 id2 分组并使用另一个数据框和日期应用函数
【发布时间】:2021-06-11 19:24:06
【问题描述】:

我的问题如下: 我有交通事故 (id_accident) 和乘客受害者 (id_victim) 的数据框 DF1 和事故日期 (date1)。

id_accident id_victim date_accident ROL
123 23A 2021/20/01 PASSENGER
456 12B 2020/19/08 PASSENGER
111 41A 2021/20/01 PASSENGER
222 54B 2020/19/08 PASSENGER

我有另一个数据框 DF2 相同的车祸和更多 (id_accident) 和一般的 VICTIMS(可能是 ROLE_VICTIM = PASSENGER 或司机)和事故发生的日期(date1

id_accident id_victim date_accident ROL
001 23A 2020/20/19 PASSENGER
002 12B 2019/31/12 DRIVER
003 41A 2020/20/12 PASSENGER
004 54B 2020/20/07 DRIVER

因此,我需要为每个 id_accident 和 id_passenger 查找该乘客是否在过去 3 个月内发生过事故,但现在为 ROLE_VICTIM =DRIVER。

我的代码包含两个循环和一个函数,当这次事故的受害者是上一次事故的司机时,该函数会搜索以前的事故。

def siniestros_anteriores(DF2,dni_victima,date_accident):

result = DF2.loc[(DF2.siniestro_fecha_ocurrencia >= date_accident-  pd.Timedelta(90, unit='d')) &
                (DF2.siniestro_fecha_ocurrencia < date_accident) &
      (DF2.poreservable_victima_dni == dni_victima) & 
      (DF2.poreservable_victima_condicion_desc =="DRIVER")] 

    if result.shape[0]==0:# si no encuentra nada--> no se activa la regla
    return 0
else:
    return 1

for id_sin in DF1.siniestro_id.unique():
    df = DF1.loc[DF1.siniestro_id ==id_sin,:]
    date_accident= df.loc[df.siniestro_id==id_sin,'siniestro_fecha_ocurrencia'].values[0]
    for dni in df.poreservable_victima_dni.unique():
        if (dni == "?") | (pd.isna(dni)):# si no hay dni--> directamente la regla es 0
            result = [id_sin, dni, 0] 
        else:
            r = siniestros_anteriores(DF2,dni,date_accident)
            result = [id_sin,dni,r]
    results.append(result)

有没有解决这个问题的有效方法?也许做一个 groupby + apply...但它不起作用...提前谢谢!

【问题讨论】:

  • 您可以将数据样本作为文本发布吗?到目前为止,您尝试过什么?
  • @crayxt 我刚刚编辑了它:)

标签: python pandas function date


【解决方案1】:

这看起来像是经典的 SQL 问题。你需要什么样的输出格式?

如果 DF2 为2020/20/01,我必须将第一次约会更改为让熊猫识别它。 下面是使用pd.merge的完整示例

import pandas as pd
import numpy as np

from io import StringIO

df1 = pd.read_csv(StringIO("""id_accident   id_victim   date_accident   ROL
123     23A     2021/20/01  PASSENGER
456     12B     2020/19/08  PASSENGER
111     41A     2021/20/01  PASSENGER
222     54B     2020/19/08  PASSENGER"""), sep="\s+", parse_dates=["date_accident"], dayfirst=True)


df2 = pd.read_csv(StringIO("""id_accident   id_victim   date_accident   ROL
001     23A     2020/20/09  PASSENGER
002     12B     2019/31/12  DRIVER
003     41A     2020/20/12  PASSENGER
004     54B     2020/20/07  DRIVER"""), sep="\s+", parse_dates=["date_accident"], dayfirst=True)

df3 = df1.merge(df2, on="id_victim")

现在df3等于

   id_accident_x id_victim date_accident_x      ROL_x  id_accident_y date_accident_y      ROL_y
0            123       23A      2021/20/01  PASSENGER              1      2020/20/19  PASSENGER
1            456       12B      2020/19/08  PASSENGER              2      2019/31/12     DRIVER
2            111       41A      2021/20/01  PASSENGER              3      2020/20/12  PASSENGER
3            222       54B      2020/19/08  PASSENGER              4      2020/20/07     DRIVER

并根据您的条件过滤掉

>>> df3[(df3.ROL_x == "PASSENGER") & (df3.ROL_y == "DRIVER") & ((df3.date_accident_y - df3.date_accident_y).dt.days < 90)]
   id_accident_x id_victim date_accident_x      ROL_x  id_accident_y date_accident_y   ROL_y
1            456       12B      2020-08-19  PASSENGER              2      2019-12-31  DRIVER
3            222       54B      2020-08-19  PASSENGER              4      2020-07-20  DRIVER

【讨论】:

    猜你喜欢
    • 2019-06-19
    • 2015-07-12
    • 1970-01-01
    • 2019-10-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-11-23
    • 1970-01-01
    相关资源
    最近更新 更多