Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Pandas 通过筛选,计算每个类别、持续时间,并根据日期确定倒数第二个_Pandas_Pandas Groupby - Fatal编程技术网

Pandas 通过筛选,计算每个类别、持续时间,并根据日期确定倒数第二个

Pandas 通过筛选,计算每个类别、持续时间,并根据日期确定倒数第二个,pandas,pandas-groupby,Pandas,Pandas Groupby,我有一个数据框,如下所示 ID Status Date Cost 0 1 F 2017-06-22 500 1 1 M 2017-07-22 100 2 1 P 2017-10-22 100 3 1 F 2018-06-22 600 4 1 M 2018-08-22 150 5 1 P 2018-10-22 120 6 1 F

我有一个数据框,如下所示

   ID   Status  Date        Cost
0   1   F       2017-06-22  500
1   1   M       2017-07-22  100
2   1   P       2017-10-22  100
3   1   F       2018-06-22  600
4   1   M       2018-08-22  150
5   1   P       2018-10-22  120
6   1   F       2019-03-22  750
7   2   M       2017-06-29  200
8   2   F       2017-09-29  600
9   2   F       2018-01-29  500
10  2   M       2018-03-29  100
11  2   P       2018-08-29  100
12  2   M       2018-10-29  100
13  2   F       2018-12-29  500
14  3   M       2017-03-20  300
15  3   F       2018-06-20  700
16  3   P       2018-08-20  100
17  3   M       2018-10-20  250
18  3   F       2018-11-20  100
19  3   P       2018-12-20  100
20  3   F       2019-03-20  600
21  3   M       2019-05-20  200
22  4   M       2017-08-10  800
23  4   F       2018-06-10  100
24  4   P       2018-08-10  120
25  4   F       2018-10-10  500
26  4   M       2019-01-10  200
27  4   F       2019-06-10  600
ID  Status  Date        Cost
0   1   F   2017-06-22  500
1   1   M   2017-07-22  100
2   1   P   2017-10-22  100
3   1   F   2018-06-22  600
4   1   M   2018-08-22  150
5   1   P   2018-10-22  120
6   1   F   2019-03-22  750
7   2   M   2017-06-29  200
8   2   F   2017-09-29  600
9   2   F   2018-01-29  500
10  2   M   2018-03-29  100
11  2   P   2018-08-29  100
12  2   M   2018-10-29  100
13  2   F   2018-12-29  500
14  3   M   2017-03-20  300
15  3   F   2018-06-20  700
16  3   P   2018-08-20  100
17  3   M   2018-10-20  250
18  3   F   2018-11-20  100
19  3   P   2018-12-20  100
20  3   F   2019-03-20  600
22  4   M   2017-08-10  800
23  4   F   2018-06-10  100
24  4   P   2018-08-10  120
25  4   F   2018-10-10  500
26  4   M   2019-01-10  200
27  4   F   2019-06-10  600
在哪里

F=故障

M=维护

p=计划

步骤1-如果最后一个raw per ID不是F,则忽略这些行,如下所示

   ID   Status  Date        Cost
0   1   F       2017-06-22  500
1   1   M       2017-07-22  100
2   1   P       2017-10-22  100
3   1   F       2018-06-22  600
4   1   M       2018-08-22  150
5   1   P       2018-10-22  120
6   1   F       2019-03-22  750
7   2   M       2017-06-29  200
8   2   F       2017-09-29  600
9   2   F       2018-01-29  500
10  2   M       2018-03-29  100
11  2   P       2018-08-29  100
12  2   M       2018-10-29  100
13  2   F       2018-12-29  500
14  3   M       2017-03-20  300
15  3   F       2018-06-20  700
16  3   P       2018-08-20  100
17  3   M       2018-10-20  250
18  3   F       2018-11-20  100
19  3   P       2018-12-20  100
20  3   F       2019-03-20  600
21  3   M       2019-05-20  200
22  4   M       2017-08-10  800
23  4   F       2018-06-10  100
24  4   P       2018-08-10  120
25  4   F       2018-10-10  500
26  4   M       2019-01-10  200
27  4   F       2019-06-10  600
ID  Status  Date        Cost
0   1   F   2017-06-22  500
1   1   M   2017-07-22  100
2   1   P   2017-10-22  100
3   1   F   2018-06-22  600
4   1   M   2018-08-22  150
5   1   P   2018-10-22  120
6   1   F   2019-03-22  750
7   2   M   2017-06-29  200
8   2   F   2017-09-29  600
9   2   F   2018-01-29  500
10  2   M   2018-03-29  100
11  2   P   2018-08-29  100
12  2   M   2018-10-29  100
13  2   F   2018-12-29  500
14  3   M   2017-03-20  300
15  3   F   2018-06-20  700
16  3   P   2018-08-20  100
17  3   M   2018-10-20  250
18  3   F   2018-11-20  100
19  3   P   2018-12-20  100
20  3   F   2019-03-20  600
22  4   M   2017-08-10  800
23  4   F   2018-06-10  100
24  4   P   2018-08-10  120
25  4   F   2018-10-10  500
26  4   M   2019-01-10  200
27  4   F   2019-06-10  600
现在,对于每个id,最后一个状态是失败

然后根据上面的df,我想准备下面的数据框

ID  No_of_F  No_of_M  No_of_P  SLS  NoDays_to_SLS NoDays_SLS_to_LS
1   3        2        2        P    487           151
2   3        3        2        M    487           61
3   3        2        2        P    640           90
4   3        1        1        M    518           151
SLS=最后一个状态

LS=最后状态

我尝试了以下代码来计算持续时间

df['Date'] = pd.to_datetime(df['Date'])
df = df.sort_values(['ID', 'Date', 'Status'])
df['D'] = df.groupby('ID')['Date'].diff().dt.days


ID  Status  Date    Cost    D
0   1   F   2017-06-22  500 nan
1   1   M   2017-07-22  100 30.00
2   1   P   2017-10-22  100 92.00
3   1   F   2018-06-22  600 243.00
4   1   M   2018-08-22  150 61.00
5   1   P   2018-10-22  120 61.00
6   1   F   2019-03-22  750 151.00
7   2   M   2017-06-29  200 nan
8   2   F   2017-09-29  600 92.00
9   2   F   2018-01-29  500 122.00
10  2   M   2018-03-29  100 59.00
11  2   P   2018-08-29  100 153.00
12  2   M   2018-10-29  100 61.00
13  2   F   2018-12-29  500 61.00
14  3   M   2017-03-20  300 nan
15  3   F   2018-06-20  700 457.00
16  3   P   2018-08-20  100 61.00
17  3   M   2018-10-20  250 61.00
18  3   F   2018-11-20  100 31.00
19  3   P   2018-12-20  100 30.00
20  3   F   2019-03-20  600 90.00
21  3   M   2019-05-20  200 61.00
22  4   M   2017-08-10  800 nan
23  4   F   2018-06-10  100 304.00
24  4   P   2018-08-10  120 61.00
25  4   F   2018-10-10  500 61.00
26  4   M   2019-01-10  200 92.00
27  4   F   2019-06-10  600 151.00
您可以使用和创建一个掩码来过滤您的
数据帧

s = df.Status.eq('F').groupby(df.ID).cumsum().groupby(df.ID).transform('idxmax')
mask = s.index <= s
df_filtered = df[mask]
[外]


另一种方法。它不要求最后一行是“F”,因此不需要.iloc[-2]:

# the following two lines are only required if the date column is a string
# and the dataframe is not already sorted
df['Date']= df['Date'].astype('datetime64')
df.sort_values(['ID', 'Date'], axis='index', ascending=True, inplace=True)

# add some auxillary columns
df['aux_date']= df['Date'].where(df['Status'] != 'F', pd.NaT)
df= pd.concat([df, pd.get_dummies(df['Status'])], axis='columns')

# calculate the relevant dates and the sums of the statuses
grouped= df.groupby('ID')
aggregated= grouped.agg({'Date': 'min', 'aux_date': 'max', 'No_of_F': 'sum', 'No_of_M': 'sum', 'No_of_P': 'sum'})
aggregated['max_date']= grouped['Date'].apply(max)

# calculate the date differences
aggregated.loc[~aggregated['aux_date'].isnull(), 'NoDays_to_SLS']=    aggregated['aux_date'] - aggregated['Date']
aggregated.loc[~aggregated['aux_date'].isnull(), 'NoDays_SLS_to_LS']= aggregated['max_date'] - aggregated['aux_date']

# drop the columns that were just inserted for calculation
aggregated.drop(['Date', 'aux_date', 'max_date'], axis='columns', inplace=True)
输出为:

    No_of_F  No_of_M  No_of_P NoDays_to_SLS NoDays_SLS_to_LS
ID                                                          
1         3        2        2      487 days         151 days
2         3        3        1      487 days          61 days
3         3        2        2      640 days          90 days
4         3        2        1      518 days         151 days
5         2        2        2      487 days           0 days
注意:我插入ID 5是为了说明我的意思,即我不依赖最后一条记录作为F。ID 5只是ID 1行中最后一条F行被删除的一个副本。这就是为什么该行的
NoDays\u SLS\u to\u LS
为零

NoDays…
-列的类型为timedelta64。如果希望将它们存储为int,可以执行以下操作:

aggregated['NoDays_to_SLS']=    aggregated['NoDays_to_SLS'].dt.days
aggregated['NoDays_SLS_to_LS']= aggregated['NoDays_SLS_to_LS'].dt.days

您好,您所说的“Step1-如果最后一个raw per ID不是F,则忽略行,预期在此之后输出,如下所示”是什么意思。顺便说一句,你在这句话下面列出的表格似乎正是你的输入表格,是设计的,还是复制粘贴的问题?是不是,你想计算每个组的所有F,M,P,但对于日期计算,你想使用最后一个非F元素?@jottbe Step1只是为了解释我是如何得到预期输出的,因为它有两个无M列。第二个No_of_M列是错误的。这不是必需的。唯一可能发生这种情况的方法是使用前导/尾随空格或“M”的不同大小写。。。检查是否没有空白?例如“M”或“M”(注意空格)