tutorial tablas seleccionar recorrer notebook graficar filtrar español documentacion datos data con columnas python pandas filtering dataframe outliers

python - tablas - seleccionar columnas de un dataframe pandas



Detectar y excluir valores atípicos en el marco de datos de Pandas (10)

Esta respuesta es similar a la proporcionada por @tanemaki, pero usa una expresión lambda lugar de scipy stats .

df = pd.DataFrame(np.random.randn(100, 3), columns=list(''ABC'')) df[df.apply(lambda x: np.abs(x - x.mean()) / x.std() < 3).all(axis=1)]

Para filtrar el DataFrame donde solo UNA columna (por ejemplo, "B") se encuentra dentro de tres desviaciones estándar:

df[((df.B - df.B.mean()) / df.B.std()).abs() < 3]

Tengo un marco de datos de pandas con pocas columnas.

Ahora sé que ciertas filas son valores atípicos basados ​​en un cierto valor de columna.

Por ejemplo, columnas: ''Vol'' tiene todos los valores alrededor de 12.xx y un valor que es 4000

Ahora me gustaría excluir aquellas filas que tienen Vol Column como esta.

Entonces, esencialmente necesito poner un filtro para que seleccionemos todas las filas donde los valores de una cierta columna están dentro de, digamos, 3 desviaciones estándar de la media.

¿Cuál es una manera elegante de lograr esto?


Mi función para eliminar valores atípicos

def drop_outliers(df, field_name): distance = 1.5 * (np.percentile(df[field_name], 75) - np.percentile(df[field_name], 25)) df.drop(df[df[field_name] > distance + np.percentile(df[field_name], 75)].index, inplace=True) df.drop(df[df[field_name] < np.percentile(df[field_name], 25) - distance].index, inplace=True)


Otra opción es transformar sus datos para que el efecto de los valores atípicos se mitigue. Usted puede hacer esto al personalizar sus datos.

import pandas as pd from scipy.stats import mstats %matplotlib inline test_data = pd.Series(range(30)) test_data.plot()

# Truncate values to the 5th and 95th percentiles transformed_test_data = pd.Series(mstats.winsorize(test_data, limits=[0.05, 0.05])) transformed_test_data.plot()


Para cada columna de su marco de datos, puede obtener cuantil con:

q = df["col"].quantile(0.99)

y luego filtrar con:

df[df["col"] < q]


Si le gusta el método de encadenamiento, puede obtener su condición booleana para todas las columnas numéricas como esta:

df.sub(df.mean()).div(df.std()).abs().lt(3)

Cada valor de cada columna se convertirá en True/False función de si está a menos de tres desviaciones estándar de la media o no.


Si tiene varias columnas en su marco de datos y desea eliminar todas las filas que tienen valores atípicos en al menos una columna, la siguiente expresión lo haría de una vez.

df = pd.DataFrame(np.random.randn(100, 3)) from scipy import stats df[(np.abs(stats.zscore(df)) < 3).all(axis=1)]


un ejemplo completo con datos y 2 grupos a continuación:

Importaciones:

from StringIO import StringIO import pandas as pd #pandas config pd.set_option(''display.max_rows'', 20)

Ejemplo de datos con 2 grupos: G1: Grupo 1. G2: Grupo 2:

TESTDATA = StringIO("""G1;G2;Value 1;A;1.6 1;A;5.1 1;A;7.1 1;A;8.1 1;B;21.1 1;B;22.1 1;B;24.1 1;B;30.6 2;A;40.6 2;A;51.1 2;A;52.1 2;A;60.6 2;B;80.1 2;B;70.6 2;B;90.6 2;B;85.1 """)

Leer datos de texto en el marco de datos de pandas:

df = pd.read_csv(TESTDATA, sep=";")

Defina los valores atípicos utilizando desviaciones estándar

stds = 1.0 outliers = df[[''G1'', ''G2'', ''Value'']].groupby([''G1'',''G2'']).transform( lambda group: (group - group.mean()).abs().div(group.std())) > stds

Defina los valores de datos filtrados y los valores atípicos:

dfv = df[outliers.Value == False] dfo = df[outliers.Value == True]

Imprimir el resultado:

print ''/n''*5, ''All values with decimal 1 are non-outliers. In the other hand, all values with 6 in the decimal are.'' print ''/nDef DATA:/n%s/n/nFiltred Values with %s stds:/n%s/n/nOutliers:/n%s'' %(df, stds, dfv, dfo)


scipy.stats tiene los métodos trim1() y trimboth() para cortar los valores atípicos en una sola fila, de acuerdo con el ranking y un porcentaje introducido de valores eliminados.


Use la indexación boolean como lo haría en numpy.array

df=pd.DataFrame({''Data'':np.random.normal(size=200)}) #example dataset of normally distributed data. df[np.abs(df.Data-df.Data.mean())<=(3*df.Data.std())] #keep only the ones that are within +3 to -3 standard deviations in the column ''Data''. df[~(np.abs(df.Data-df.Data.mean())>(3*df.Data.std()))] #or if you prefer the other way around

Para una serie es similar:

S=pd.Series(np.random.normal(size=200)) S[~((S-S.mean()).abs()>3*S.std())]


#------------------------------------------------------------------------------ # accept a dataframe, remove outliers, return cleaned data in a new dataframe # see http://www.itl.nist.gov/div898/handbook/prc/section1/prc16.htm #------------------------------------------------------------------------------ def remove_outlier(df_in, col_name): q1 = df_in[col_name].quantile(0.25) q3 = df_in[col_name].quantile(0.75) iqr = q3-q1 #Interquartile range fence_low = q1-1.5*iqr fence_high = q3+1.5*iqr df_out = df_in.loc[(df_in[col_name] > fence_low) & (df_in[col_name] < fence_high)] return df_out