【问题标题】:Calculating across rows and columns at same time同时跨行和列计算
【发布时间】:2019-07-29 18:17:32
【问题描述】:

我正在尝试在 python 中跨行和列进行一些计算。执行大型数据集需要花费更长的时间。

我正在尝试进行如下计算:

Df =pd.DataFrame({'A': [1,1,1,2,2,2,2],
                   'unit': [1,2,1,1,1,1,2],
                   'D1':[100,100,100,200,300,400,3509],
                   'D2':[200,200,200,300,300,400,2500],
                   'D3':[50,50,50,60,50,67,98],
                   'Level1':[1,4,0,4,4,4,5],
                   'Level2':[45,3,0,6,7,8,9],
                   'Level3':[0,0,34,8,7,0,5]
                 })

对于 A 的每个值(在上面的示例中,A=1 和 2)我按顺序运行一个函数(即,由于 A 的结果,我不能同时为 A=1 和 A=2 运行相同的函数=1 改变了 A=2) 的一些其他值。我将分数计算为:

def score(data):
    data['score_Level1']=np.where(data['Level1']>=data['unit'], data['unit'], 0)*(((np.where(data['Level1']>=data['unit'], data['unit'], 0)).sum()*100) +(10/data['D1']))
    data['score_Level2']=np.where(data['Level2']>=data['unit'], data['unit'], 0)*(((np.where(data['Level2']>=data['unit'], data['unit'], 0)).sum()*100) +(10/data['D2']))
    data['score_Level3']=np.where(data['Level3']>=data['unit'], data['unit'], 0)*(((np.where(data['Level3']>=data['unit'], data['unit'], 0)).sum()*100) +(10/data['D3']))

    return(data)

以上代码的作用是逐行计算Leveli (i=1,2,3)的分数,如下所示:

Step1:
compare Value of "Leveli' with corresponding "unit" column, if Leveli >=unit then unit else 0. 

Step2:
Then it (sums up result for above operation across all rows for Leveli)*100+ (1/Di) = Lets say "S"

Step3:
It goes row by row again and assign a score for Leveli as:

Step1*Step2 (for each row)

Above code should yield results for A=1 as:

score(Df[Df['A']==1])

I am listing only scoring for Level1, same thing happends for Level2 and Level3
Step1:
Compare 1>=1 = True Yields 1, 4>=2 = true Yields 2, 0>=1 =False Yields 0

Step2:
(1+2+0)*100+1/100=300.1

Step3:
Compare 1>=1 = True Yields 1 *300.1=300.1
Compare 4>=2 = True Yields 2 *300.1=600.2
Compare 0>=1 = False Yields 0 *300.1=0

我正在为 2 亿个 A 值执行此活动。由于它必须按顺序完成(A=n 取决于 A=n-1 的结果),因此计算需要很长时间。

非常感谢任何让它更快的建议。

【问题讨论】:

    标签: python-3.x pandas numpy-ndarray


    【解决方案1】:

    我认为,您可以避免 where 应该运行得更快。 你能试试这个代码吗:

    def score2(data, score_field, level_field, d_field):
        indexer= data[level_field]>=data['unit']
        data[score_field]= 0.0
        data.loc[indexer, score_field]= data['unit'] * data.loc[indexer, 'unit'].sum()*100 + 10/data[d_field]
        return(data)
    
    score2(Df, 'score_Level1', 'Level1', 'D1')
    score2(Df, 'score_Level2', 'Level2', 'D2')
    score2(Df, 'score_Level3', 'Level3', 'D3')
    

    .loc 与索引器组合替换了 where。在分配的左侧,它只会设置“级别字段”大于unit 的行的值。所有其他人都保持原样。如果没有data[score_field]= 0.0 行,它们将包含NaN。 顺便提一句。 pandas 有自己的.where 方法,适用于系列。它与numpy 的实现略有不同。

    【讨论】:

    • 谢谢。我试过了,但没有改善运行时间:(
    • 对不起,那我帮不了你了。但也许您可以检查是否可以并行化任务,或者是否可以分块处理数据。第一个选项可能是 dask 的解决方案(不确定您是否可以使用它),第二个选项类似于 read_csv 的“块大小”。请检查您的数据源是否也提供类似的内容。但无论如何,对于sum()-part,您无论如何都需要遍历整个数据框。
    猜你喜欢
    • 2011-05-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-01-06
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多