查找每行中特定列的最大值,并将相应列的值与另一列的值相匹配

2024-09-28 01:27:35 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一张这样的桌子

Hour表示代理成功到达客户的时间

Cus1到Cus4是提供给代理打电话给客户的前4个时隙

Cus1_分数到Cus4_分数表示在对应于Cus1到Cus4的小时内呼叫成功的概率

我需要得到Match1和Match2列的是或否值

Match1表示这一点-检查Cus1到Cus4列中的最高分数。如果没有重复项,请检查Cus1=Hour是否匹配,如果匹配,我们写“是”,否则写“否”。如果存在重复项,请检查所有得分最高的列,并检查小时数是否匹配Cus列(Cus1到Cus4)中的高分值。再说一次,如果是匹配的是,否则不是

Match2表示这一点-检查Cus1到Cus4列中第二高的分数。如果没有重复项,请检查Cus2=小时,如果匹配,我们写“是”,否则写“否”。如果存在重复项,请检查所有得分第二高的列,并检查小时数是否匹配第二高分表示的Cus列(Cus1到Cus4)中的任何值。再说一次,如果是匹配的是,否则不是

ID   Hour  Cus1  Cus2  Cus3  Cus4  Cus1_Score  Cus2_Score  Cus3_Score  Cus4_Score  Match1  Match2

1     11    8     10    11    14      0.62        0.59        0.59        0.54       NO     YES 

2     13    15    16    18    13      0.57        0.57        0.57        0.57       YES    NO

3     16    09    14    16    12      0.67        0.54        0.48        0.34       NO     NO

4     08    11    08    12    17      0.58        0.55        0.43        0.25       NO     YES

我尝试过使用idxmax()和nlargest(2)函数,但运气不佳,因为我对Python不是很在行。非常感谢你的帮助


Tags: no代理客户分数yesscore小时hour
2条回答

希望我得到了正确的条件;下面的计算依赖于赋值前的索引;因此,我创建了一个长数据帧,创建了长数据帧的条件,将大小减少到唯一索引,并将结果分配给原始数据帧:

创建一个长数据框来计算条件(为了方便起见,我在这里使用pyjanitorpivot_longer对其进行重塑;您可以在不使用PyGatitor的情况下通过几个步骤来完成这项工作):

# pip install git+https://github.com/pyjanitor-devs/pyjanitor.git
import janitor as jn
import pandas as pd
res = (df.pivot_longer(['ID', 'Hour'], 
                       names_pattern= [r'.+\d$', r'.+Score$'], 
                       names_to = ['cus', 'score'], 
                       ignore_index = False)
       )

print(res)

   ID  Hour  cus  score
0   1    11    8   0.62
1   2    13   15   0.57
2   3    16    9   0.67
3   4     8   11   0.58
0   1    11   10   0.59
1   2    13   16   0.57
2   3    16   14   0.54
3   4     8    8   0.55
0   1    11   11   0.59
1   2    13   18   0.57
2   3    16   16   0.48
3   4     8   12   0.43
0   1    11   14   0.54
1   2    13   13   0.57
2   3    16   12   0.34
3   4     8   17   0.25

match1创建条件:

# get booleans for max and no duplicates
res = res.sort_index()
max1 = res.groupby(level=0).score.transform('max')
# max without duplicates
cond1 = res.score.eq(max1).groupby(level=0).sum().eq(1)
cond1 = cond1 & df.Hour.eq(df.Cus1)
# max with duplicates
cond2 = res.score.eq(max1).groupby(level=0).transform('sum').gt(1) 
cond2 &= res.Hour.eq(res.cus)
cond2 = cond2.groupby(level=0).any()
df['match1'] = np.where(cond1 | cond2, 'YES', 'NO')

匹配2:


second_largest = (res.sort_values('score', ascending=False)
                     .groupby(level=0, sort = False)
                     .score
                     .transform('nth', 1)
                  )
second_largest = second_largest.sort_index()
# second largest without duplicates
cond_1 = res.score.eq(second_largest).groupby(level=0).sum().eq(1)
cond_1 &= df.Hour.eq(df.Cus2)
# second largest with duplicates
cond_2 = res.score.eq(second_largest).groupby(level=0).transform('sum').gt(1)
cond_2 &= res.Hour.eq(res.cus)
cond_2 = cond_2.groupby(level=0).any()
df['match2'] = np.where(cond_1 | cond_2, 'YES', 'NO')
df

      ID  Hour  Cus1  Cus2  Cus3  Cus4  Cus1_Score  Cus2_Score  Cus3_Score  Cus4_Score match1 match2
0   1    11     8    10    11    14        0.62        0.59        0.59        0.54     NO    YES
1   2    13    15    16    18    13        0.57        0.57        0.57        0.57    YES    YES
2   3    16     9    14    16    12        0.67        0.54        0.48        0.34     NO     NO
3   4     8    11     8    12    17        0.58        0.55        0.43        0.25     NO    YES

您需要为行操作编写一个函数,其中包含您解释的所有条件。然后,您可以使用.iterrowsfor.apply方法将此函数应用于行,您可以找到它们here

相关问题 更多 >

    热门问题