Rodando una función en un dataframe

Tengo el siguiente dataframe C

 >>> C abc 2011-01-01 0 0 NaN 2011-01-02 41 12 NaN 2011-01-03 82 24 NaN 2011-01-04 123 36 NaN 2011-01-05 164 48 NaN 2011-01-06 205 60 2 2011-01-07 246 72 4 2011-01-08 287 84 6 2011-01-09 328 96 8 2011-01-10 369 108 10 

Me gustaría agregar una nueva columna, d , donde aplico una función de rotación, en una ventana fija (6 aquí), donde de alguna manera, para cada fila (o fecha), fijo el valor c . Un bucle en esta función de balanceo debe ser (pseudo):

  abcd 2011-01-01 0 0 NaN a + b*2 (a,b from this row, '2' is from 'c' on 2011-01-06) 2011-01-02 41 12 NaN a + b*2 (a,b from this row, '2' is still from 2011-01-06) 2011-01-03 82 24 NaN a + b*2 2011-01-04 123 36 NaN a + b*2 2011-01-05 164 48 NaN a + b*2 2011-01-06 205 60 2 a + b*2 2011-01-07 246 72 4 2011-01-08 287 84 6 2011-01-09 328 96 8 2011-01-10 369 108 10 

Después de este “bucle”, quiero tomar todas estas 6 filas calculadas en d y ejecutar una llamada de función, que a su vez devolverá un valor, que debe almacenarse en otra columna, digamos:

  abcde 2011-01-01 0 0 NaN a + b*2 ---| NaN 2011-01-02 41 12 NaN a + b*2 | NaN 2011-01-03 82 24 NaN a + b*2 | These values NaN 2011-01-04 123 36 NaN a + b*2 | are input to NaN 2011-01-05 164 48 NaN a + b*2 | function NaN 2011-01-06 205 60 2 a + b*2 ---| yielding X 2011-01-07 246 72 4 value X in 2011-01-08 287 84 6 column 'e' 2011-01-09 328 96 8 2011-01-10 369 108 10 

Este procedimiento luego se iteraría en la siguiente ventana (de nuevo 6 de largo) como:

  abcde 2011-01-01 0 0 NaN 2011-01-02 41 12 NaN a + b*4 (a,b from this row, '4' is from 'c' now from 2011-01-07) 2011-01-03 82 24 NaN a + b*4 (a,b from this row, '4' is still from 2011-01-07) 2011-01-04 123 36 NaN a + b*4 2011-01-05 164 48 NaN a + b*4 2011-01-06 205 60 2 a + b*4 X 2011-01-07 246 72 4 a + b*4 2011-01-08 287 84 6 2011-01-09 328 96 8 2011-01-10 369 108 10 abcde 2011-01-01 0 0 NaN NaN 2011-01-02 41 12 NaN a + b*4 ---| NaN 2011-01-03 82 24 NaN a + b*4 | These values NaN 2011-01-04 123 36 NaN a + b*4 | are input to NaN 2011-01-05 164 48 NaN a + b*4 | function NaN 2011-01-06 205 60 2 a + b*4 | yielding X 2011-01-07 246 72 4 a + b*4 ---| value Y in Y 2011-01-08 287 84 6 column 'e' 2011-01-09 328 96 8 2011-01-10 369 108 10 

Esperemos que esto sea lo suficientemente claro,

Gracias n

Podrías usar pd.rolling_apply :

 import numpy as np import pandas as pd df = pd.read_table('data', sep='\s+') def foo(x, df): window = df.iloc[x] # print(window) c = df.ix[int(x[-1]), 'c'] dvals = window['a'] + window['b']*c return bar(dvals) def bar(dvals): # print(dvals) return dvals.mean() df['e'] = pd.rolling_apply(np.arange(len(df)), 6, foo, args=(df,)) print(df) 

rendimientos

  abce 2011-01-01 0 0 NaN NaN 2011-01-02 41 12 NaN NaN 2011-01-03 82 24 NaN NaN 2011-01-04 123 36 NaN NaN 2011-01-05 164 48 NaN NaN 2011-01-06 205 60 2 162.5 2011-01-07 246 72 4 311.5 2011-01-08 287 84 6 508.5 2011-01-09 328 96 8 753.5 2011-01-10 369 108 10 1046.5 

Los parámetros args y kwargs se agregaron a rolling_apply en Pandas versión 0.14.0 .

Como en mi ejemplo anterior, df es una variable global, no es realmente necesario pasarla a foo como un argumento. Simplemente puede eliminar df de la línea def foo y también omitir args=(df,) en la llamada a rolling_apply .

Sin embargo, hay ocasiones en que df podría no estar definido en un ámbito accesible por foo . En ese caso, hay una solución simple: hacer un cierre:

 def foo(df): def inner_foo(x): window = df.iloc[x] # print(window) c = df.ix[int(x[-1]), 'c'] dvals = window['a'] + window['b']*c return bar(dvals) return inner_foo df['e'] = pd.rolling_apply(np.arange(len(df)), 6, foo(df))