2012-06-13 24 views
5

Recientemente me enteré de pandas y me complació ver su funcionalidad de análisis. Estoy intentando convertir las funciones de matriz de Excel en el equivalente de Pandas para automatizar las hojas de cálculo que he creado para la creación de informes de atribución de rendimiento. En este ejemplo, he creado una nueva columna en Excel basado en las condiciones dentro de otras columnas:Crear RESÚMENES similares a Excel en Pandas

={SUMIFS($F$10:$F$4518,$A$10:$A$4518,$C$4,$B$10:$B$4518,0,$C$10:$C$4518," ",$D$10:$D$4518,$D10,$E$10:$E$4518,$E10)} 

La fórmula está resumiendo los valores de la matriz "F" (pesos de seguridad) en base a ciertas condiciones. "A" matriz (ID de cartera) es un cierto número, matriz "B" (identificación de seguridad) es cero, matriz "C" (descripción de grupo) es "", matriz "D" (fecha de inicio) es la fecha de la fila que estoy encendido, y la matriz "E" (fecha de finalización) es la fecha de la fila en la que estoy.

En Pandas, estoy usando el DataFrame. Crear una nueva columna en un marco de datos con las tres primeras condiciones es sencillo, pero estoy teniendo problemas con las dos últimas condiciones.

reportAggregateDF['PORT_WEIGHT'] = reportAggregateDF['SEC_WEIGHT_RATE'] 
      [(reportAggregateDF['PORT_ID'] == portID) & 
      (reportAggregateDF['SEC_ID'] == 0) & 
      (reportAggregateDF['GROUP_LIST'] == " ") & 
      (reportAggregateDF['START_DATE'] == reportAggregateDF['START_DATE'].ix[:]) & 
      (reportAggregateDF['END_DATE'] == reportAggregateDF['END_DATE'].ix[:])].sum() 

Obviamente, el .ix [:] en las dos últimas condiciones no está haciendo nada para mí, pero no es la manera de hacer la suma condicionada a la fila que estoy en un bucle sin? Mi objetivo es no hacer ningún bucle, sino utilizar operaciones puramente vectoriales.

Respuesta

1

Estoy seguro de que hay una manera mejor, pero esto lo hice en un bucle:

for idx, eachRecord in reportAggregateDF.T.iteritems(): 
reportAggregateDF['PORT_WEIGHT'].ix[idx] = reportAggregateDF['SEC_WEIGHT_RATE'][(reportAggregateDF['PORT_ID'] == portID) &    
    (reportAggregateDF['SEC_ID'] == 0) &    
    (reportAggregateDF['GROUP_LIST'] == " ") &    
    (reportAggregateDF['START_DATE'] == reportAggregateDF['START_DATE'].ix[idx]) &    
    (reportAggregateDF['END_DATE'] == reportAggregateDF['END_DATE'].ix[idx])].sum() 
6

Usted desea utilizar la función y una lambda se aplican:

>> df 
    A B C D  E 
0 mitfx 0 200 300 0.25 
1  gs 1 150 320 0.35 
2 duk 1 5 2 0.45 
3 bmo 1 145 65 0.65 

Digámosme quiere resumir la columna C e tiempos, pero sólo si la columna B == 1 y D es mayor que 5,

df['matches'] = df.apply(lambda x: x['C'] * x['E'] if x['B'] == 1 and x['D'] > 5 else 0, axis=1) 
df.matches.sum() 

podría ser más limpio a dividir este int o dos pasos:

df_subset = df[(df.B == 1) & (df.D > 5)] 
df_subset.apply(lambda x: x.C * x.E, axis=1).sum() 

o simplemente usar la multiplicación de la velocidad:

df_subset = df[(df.B == 1) & (df.D > 5)] 
print sum(df_subset.C * df_subset.E) 

tiene toda la razón para querer hacer este problema sin bucles.

Cuestiones relacionadas