熊猫进行循环优化

时间:2018-07-24 15:25:39

标签: python pandas for-loop dataframe optimization

我是python的新手,尽管我可以毫无问题地编写循环,但是我发现它们的运行速度非常慢。这是我的代码:

perc_match是一个在两个向量之间运行计算的函数,在这种情况下,这两个向量是数据帧的行。

def perc_match(customer_id,bait_name):
    score = int(df_master.loc[customer_id,:].dot(df_pim.loc[bait_name,:].values))
    perfect = int(df_master.loc[customer_id,:].dot(df_perf.iloc[0,:].values))
    if perfect == 0:
        return 0
    elif (score / perfect)*100 < 0:
        return 0
    else:
        percent = round((score / perfect)*100,3)
        percent = float(percent)
    return percent

match_maker对两个数据帧中的每一行调用perc_match,并将输出放置在df_match中的相应单元格中。

def match_maker(df_match):
    for i in df_match.index:
        for j in df_match.columns:
             df_match.loc[i,j] = perc_match(i,j)

以供参考:

df_master.shape = (122905, 33) df_pim.shape = (36, 33) df_perf.shape = (1, 33) df_match.shape = (122905, 36)

一切正常-除非我测试需要多长时间...

5.49 s ± 72 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)

当我在100,000行上运行时效果不佳。我知道有优化代码的方法,但是我很难理解它。我可以减少这些代码的最佳方法是什么?

编辑:

输入看起来像这样:

df_master

 Customer ID       Email       Technique 1       ...        Technique 33
 12345             i@me.com    1                 ...        0
 ...

df_pim

 Product ID        Technique 1        ...        Technique 33
 Product 1         1                             0
 ...

df_perc(所有值均为1):

 index             Technique 1        ...        Technique 33
                   1                             1

df_match

 Customer ID       Email       Product 1         ...        Product N
 12345             i@me.com    0                 ...        0
 ...

我希望函数编辑df_match如下所示:

df_match(根据技术值之间的比较给出%匹配):

 Customer ID       Email       Product 1         ...        Product N
 12345             i@me.com    12.842            ...        44.312
 ...

1 个答案:

答案 0 :(得分:0)

假设: 我假设在perc_match()第3行中的df_perf是一个错字,而您的意思是df_perc。

您想将事物视为要计算的单个值。您正在使用的.dot运算符可以处理2个维度以及一个维度。

在您的perc_match()中,您拥有:

score = int(df_master.loc[customer_id,:].dot(df_pim.loc[bait_name,:].values))

一次在一行上乘以另一行。如何使用以下方法制作得分数据框:

columns = ["Technique "+str(a) for a in range(1,34)]
score_df = df_master[columns].dot(df_pim)

如果要将它们乘以一个全为1的数据框,则几乎不需要完美的行。那么这样的事情呢?

perfect = int(df_master.sum(axis=0))

这会给您一些思考的时间。我待会儿会回答这个问题,否则我不在时有人可以接听。