Python

Pandas: Cambiar el tipo de columnas en un DataFrame

Al crear un nuevo DataFrame en Pandas, si no se indica de forma explícita, el constructor le asignará a cada una de las series el tipo de dato que considere más adecuado. Pudiendo ser diferente al que necesitamos. Especialmente cuando en los datos originales se combinan valores numéricos con cadenas de texto. Para solucionar estos problema y cambiar el tipo de columnas en un DataFrame se puede recurrir al método to_numeric().

Texto y valores numéricos en una serie

Cuando se crea un DataFrame en Pandas a partir de un diccionario de listas es posible que nos encontremos con un problema como el siguiente.

import pandas as pd

df = pd.DataFrame({'X': [1, '2', 3],
                   'Y': [4, 5, 6],
                   'Z': ['7', '8', '9']})
   X  Y  Z
0  1  4  7
1  2  5  8
2  3  6  9

Aparentemente se tiene tres columnas numéricas, pero al consultar el tipo de dato veremos que no es así, solamente la serie Y es de tipo entero.

df.dtypes
X    object
Y     int64
Z    object
dtype: object

El resto son objetos. Debido esto al hecho de usar textos en lugar de números para representar valores en estas dos series. Impidiendo llevar a cabo operaciones algebraicas con estas series, apareciendo un error cuando se intenta algo tan sencillo como sumar un número: df.X + 1.

Cambiar el tipo de columnas con to_numeric

Para solucionar problemas como el visto anteriormente en Pandas se puede utilizar la función to_numeric(), con la que es posible convertir una serie cualquier en una equivalente de tipo numérica. Así, para convertir la serie X de nuestro ejemplo solamente se tendría que hacer

pd.to_numeric(df.X)
0    1
1    2
2    3
Name: X, dtype: int64

Con lo que se obtiene una serie equivalente, pero de tipo entero en lugar de objeto. Siendo ya posible realizar operaciones algebraicas sobre ella.

Reducción de los datos

Generalmente el tipo de dato asignado por defecto suele ser adecuado, pero, en algunas ocasiones, puede que nos interese emplear un tipo de dato más pequeño para usar menos memoria. Por ejemplo, los valores usados hasta ahora, entre uno y nueve, se pueden representar mediante un entero de 8 bits. Un tipo de dato con el que se puede guardar 8 enteros en el espacio necesario para por un entero de 64.

La reducción del tipo de dato al más pequeño con el que se pueden representar los datos de la serie se puede forzar mediante la propiedad downcast. Propiedad que tiene las siguientes opciones:

  • None: valor por defecto y el tipo no se reduce
  • 'integer': tipo entero con signo más pequeño
  • 'unsigned': tipo entero sin signo más pequeño
  • 'float': tipo real más pequeño

Mediante el siguiente código se puede ver el resultado de aplicar las diferentes opciones en el DataFrame de ejemplo.

df.X = pd.to_numeric(df.X, downcast='float')
df.Y = pd.to_numeric(df.Y, downcast='unsigned')
df.Z = pd.to_numeric(df.Z, downcast='integer')
df.dtypes
X    float32
Y      uint8
Z       int8
dtype: object

Gestionar los errores

En los casos que no es posible convertir el dato original en uno numérico, por ejemplo, cuando uno de los valores es una palabra en lugar de un número. La función to_numeric() produciría una excepción. Los cuales se pueden gestionar mediante la propiedad errors de la función. Propiedad que tiene las siguientes opciones:

  • 'raise': ante una transformación no válida se generará una excepción.
  • 'coerce': los valores que no se pueden transformar producen un NaN.
  • 'ignore': los valores que no se pueden transformar devuelven el valor original

Así cuando se usa 'coerce' todos los valores inválidos eran un NaN.

df = pd.DataFrame({'X': [1, 'pd', 3],
                   'Y': [4, 5, 6],
                   'Z': ['7', '8', '9']})

pd.to_numeric(df.X, errors='coerce')
0    1.0
1    NaN
2    3.0
Name: X, dtype: float64

Mientras que en el caso de emplear 'ignore' los valores volverán tal cual, por lo que la serie resultante seguirá siendo de tipo objeto.

pd.to_numeric(df.X, errors='ignore')
0     1
1    pd
2     3
Name: X, dtype: object

Conclusiones

En esta entrada se ha visto un método mediante el cual se puede cambiar el tipo de columnas en un DataFrame para conseguir tipos numéricos. Lo que permite depurar los datos antes de realizar cualquier análisis. Si necesitamos convertir cadenas de texto en objetos de tipos fecha el método que necesitamos será to_datetime().

¿Te ha parecido de utilidad el contenido?

Daniel Rodríguez

Share
Published by
Daniel Rodríguez
Tags: Pandas

Recent Posts

Por Qué las Contraseñas Largas son más Seguras que las Complejas

"Tu contraseña debe tener al menos 8 caracteres, una mayúscula, un número y un símbolo…

5 días ago

Gini, KS y AUC: Cómo Medir la Calidad de un Modelo de Credit Scoring

Cuando un analista de riesgo presenta un nuevo scorecard ante el comité de dirección, la…

7 días ago

Curiosidad: De dónde vienen foo, bar y foobar

Si revisáis código o documentación de otros programadores, tarde o temprano os toparéis con dos…

2 semanas ago

BG/NBD + Gamma/Gamma: el modelo probabilístico para CLV en compras continuas

Los dos artículos anteriores cubrieron el CLV clásico —una fórmula útil pero que trata a…

2 semanas ago

Errores habituales al trabajar con DataFrames grandes en Pandas (y cómo evitarlos)

Hay un momento muy concreto en la vida de casi todo análisis: el código que…

3 semanas ago

Champion vs Challenger: Cómo los Bancos Validan Modelos Nuevos antes de Ponerlos en Producción

Has construido un nuevo modelo de credit scoring. Las métricas de validación son mejores que…

3 semanas ago

This website uses cookies.