Revista Informática

Operaciones de filtrado de DataFrame con Pandas en base a los valores de las columnas

Publicado el 10 mayo 2019 por Daniel Rodríguez @analyticslane

Los objetos DataFrame de Pandas son una herramienta fantástica para trabajar con datos. Permitiendo realizar múltiples tareas de una forma rápida y sencilla. Una de las más habituales es filtrar, poder seleccionar un subconjunto de los datos en base a los valores de uno o varias columnas. En esta entrada se explicarán diferentes formas de realizar el filtrado de DataFrame con Pandas en base a los valores de las columnas.

A modo de ejemplo en esta entrada se utilizará el conjunto de datos de exoplanetas que se puede encontrar en la librería Seaborn. Para importarlo se ha de importar la librería y utilizas la función load_dataset() como se muestra en el siguiente ejemplo

import seaborn as sb

planets = sb.load_dataset('planets')
planets.head()
            method  number  orbital_period   mass  distance  year
0  Radial Velocity       1         269.300   7.10     77.40  2006
1  Radial Velocity       1         874.774   2.21     56.95  2008
2  Radial Velocity       1         763.000   2.60     19.84  2011
3  Radial Velocity       1         326.030  19.40    110.62  2007
4  Radial Velocity       1         516.220  10.50    119.47  2009

Filtrado en base al valor de una columna

La operación básica de filtrado es seleccionar aquellos valores que cumplen una condición. Para ello se puede comparar la columna con el valor deseado y obtener una lista de valores verdaderos o falsos. Por ejemplo, en el caso de los exoplanetas se pueden seleccionar aquellos que han sido descubiertos en 2008 con el siguiente código

in_2008 = planets['year'] == 2008
in_2008.head()
0    False
1     True
2    False
3    False
4    False
Name: year, dtype: bool

Para conseguir un nuevo DataFrame solamente con estos planetas simplemente se ha de usar in_2018 como filtro. Así se puede conseguir el nuevo conjunto de datos.

planets_2008 = planets[in_2008]
planets_2008.head()
             method  number  orbital_period   mass  distance  year
1   Radial Velocity       1         874.774   2.21     56.95  2008
5   Radial Velocity       1         185.840   4.80     76.39  2008
8   Radial Velocity       1         993.300  10.30     73.10  2008
12  Radial Velocity       1         479.100   3.88     97.28  2008
27  Radial Velocity       1         952.700   5.30     97.18  2008

No es necesario guardar el filtro en una variable, simplemente se puede utilizar la operación directamente como filtro.

planets_2008 = planets[planets['year'] == 2008]

Filtrado de las columnas que no tienen un valor

De forma análoga a como se ha conseguido seleccionar los registros que cumplen una condición se puede seleccionar aquellos que no la cumple. Ahora simplemente el filtro se puede conseguir mediante el operador no igual. Así los planetas que no han sido descubiertos en 2008 se pueden obtener con el siguiente código.

planets_not_2008 = planets[planets['year'] != 2008]
planets_not_2008.head()
            method  number  orbital_period   mass  distance  year
0  Radial Velocity       1          269.30   7.10     77.40  2006
2  Radial Velocity       1          763.00   2.60     19.84  2011
3  Radial Velocity       1          326.03  19.40    110.62  2007
4  Radial Velocity       1          516.22  10.50    119.47  2009
6  Radial Velocity       1         1773.40   4.64     18.15  2002

Filtrado en base a valores nulos

En muchos conjuntos de datos es habitual que existan registros con valores nulos. Para identificar los registros nulos objetos de Pandas cuentan con los métodos isnull() y notnull(). Tal como indica el nombre, el primero de ellos devuelve verdadero en los registros nulos y el segundo en los que no son nulos. Aplicando estos métodos a una columna se puede saber los registros que cumplen una condición u otra. En el ejemplo de los exoplanetas se puede filtrar aquellos en los que no se conoce la masa con el siguiente ejemplo.

planets_null = planets[planets.mass.isnull()]
planets_null.head()
             method  number  orbital_period  mass  distance  year
7   Radial Velocity       1       798.50000   NaN     21.41  1996
20  Radial Velocity       5         0.73654   NaN     12.53  2011
25  Radial Velocity       1       116.68840   NaN     18.11  1996
26  Radial Velocity       1       691.90000   NaN     81.50  2012
29          Imaging       1             NaN   NaN     45.52  2005

Por otro lado, para obtener aquellos en los que se conoce la masa se puede utilizar.

planets_not_null = planets[planets.mass.notnull()]
planets_not_null.head()
            method  number  orbital_period   mass  distance  year
0  Radial Velocity       1         269.300   7.10     77.40  2006
1  Radial Velocity       1         874.774   2.21     56.95  2008
2  Radial Velocity       1         763.000   2.60     19.84  2011
3  Radial Velocity       1         326.030  19.40    110.62  2007
4  Radial Velocity       1         516.220  10.50    119.47  2009

Filtrados por elementos en una lista

Los filtros anteriores bastante útiles, pero en muchas ocasiones se desea seleccionar datos cuyos valores se encuentra en una lista. Para ello se puede aplicar el método isin() a las columnas para obtener un filtro. Por ejemplo, los planetas que han sido descubiertos en 2008 y 2008 son:

planets_in_years = planets[planets.year.isin([2008, 2009])]
planets_in_years.head()
             method  number  orbital_period   mass  distance  year
1   Radial Velocity       1         874.774   2.21     56.95  2008
4   Radial Velocity       1         516.220  10.50    119.47  2009
5   Radial Velocity       1         185.840   4.80     76.39  2008
8   Radial Velocity       1         993.300  10.30     73.10  2008
11  Radial Velocity       1         335.100   9.88     39.43  2009

Por otro lado, si se desea conocer los registros que no está en una lista mediante el operador negación ~ se puede invertir el filtro. Así los planetas que no han sido descubiertos en 2008 y 2009 son:

planets_not_in_years = planets[~planets.year.isin([2008, 2009])]
planets_not_in_years.head()
            method  number  orbital_period   mass  distance  year
0  Radial Velocity       1          269.30   7.10     77.40  2006
2  Radial Velocity       1          763.00   2.60     19.84  2011
3  Radial Velocity       1          326.03  19.40    110.62  2007
6  Radial Velocity       1         1773.40   4.64     18.15  2002
7  Radial Velocity       1          798.50    NaN     21.41  1996

Unión de varias condiciones

Finalmente se puede combinar varios filtros mediante el uso de los operadores & ("and") y | ("or"). Así los planetas que han sido descubiertos en 2008 o 2009 y al mismo tiempo no se conoce la masa se pueden obtener mediante el siguiente ejemplo.

planets[planets.year.isin([2008, 2009]) & planets.mass.isnull()]
                       method  number  orbital_period  mass  distance  year
33                    Imaging       1             NaN   NaN       NaN  2008
37  Eclipse Timing Variations       2          5767.0   NaN    130.72  2008
38  Eclipse Timing Variations       2          3321.0   NaN    130.72  2008
47                    Imaging       1          6000.0   NaN     19.28  2008
68                    Imaging       1        318280.0   NaN      7.69  2008

Conclusiones

En esta entrada se han visto diferentes operaciones de filtrado de DataFrame con Pandas en base a los valores de una columna. Conocer todas estas operaciones es clave para operar de forma eficiente con los objetos DataFrame de Pandas. Operaciones que complementan a otras vistas anteriormente como ordenar el contenido, comparar los registros o combinar diferentes DataFrames.

Imágenes: Pixabay (Ahmad Ardity)

No te olvides valorar esta entrada

Suscríbete a nuestro boletín

Suscríbete al boletín semanal para estar al día de todas las publicaciones de Analytics Lane.

Contenido relacionado


Volver a la Portada de Logo Paperblog