2015-07-12 87 views
4

對於一個相對較大的熊貓數據框(幾十萬行),我想創建一個應用函數的結果系列。問題是這個函數不是很快,我希望它能以某種方式加快速度。加速熊貓應用函數

df = pd.DataFrame({ 
'value-1': [1, 2, 3, 4, 5], 
'value-2': [0.1, 0.2, 0.3, 0.4, 0.5], 
'value-3': somenumbers..., 
'value-4': more numbers..., 
'choice-index': [1, 1, np.nan, 2, 1] 
}) 

def func(row): 
    i = row['choice-index'] 
    return np.nan if math.isnan(i) else row['value-%d' % i] 

df['value'] = df.apply(func, axis=1, reduce=True) 

# expected value = [1, 2, np.nan, 0.4, 5] 

歡迎任何建議。

更新

一個非常小的加速比(〜1.1)可通過預緩存選中的列來實現。

cached_columns = [None, 'value-1', 'value-2', 'value-3', 'value-4'] 
def func(row): 
    i = row['choice-index'] 
    return np.nan if math.isnan(i) else row[cached_columns[i]] 

,但我希望更大的加速......

+0

,您是否試圖用Cython,numba,EVAL + numexpr在http://pandas.pydata.org/pandas-docs/stable/enhancingperf.html – denfromufa

+0

不建議,不爲這個特殊的問題。但我認爲主要的問題是調用apply函數的次數,所以'cython','numba','numexpr'等對緩解這個問題無濟於事。 – orange

回答

4

我想我有一個很好的解決方案(加速〜150):到func會改變。

訣竅是不要使用apply,而是做智能選擇。

choice_indices = [1, 2, 3, 4] 
for idx in choice_indices: 
    mask = df['choice-index'] == idx 
    result_column = 'value-%d' % (idx) 
    df.loc[mask, 'value'] = df.loc[mask, result_column]