Python
Desmitificando NaN de Pandas: una guía para principiantes

Desmitificando NaN de Pandas: una guía para principiantes

MoeNagy Dev

Comprendiendo los conceptos básicos de pandas.isnull() y pandas.isna()

Explorando el concepto de is nan de pandas

¿Qué es pandas.isnull() y pandas.isna()?

Las funciones pandas.isnull() y pandas.isna() se utilizan para identificar valores faltantes en un DataFrame o Serie de pandas. Estas funciones devuelven una máscara booleana con la misma forma que la entrada, donde True indica un valor faltante y False indica un valor no faltante.

Aquí hay un ejemplo:

import pandas as pd
 
# Crear un DataFrame de muestra
df = pd.DataFrame({'A': [1, 2, None, 4], 'B': [5, None, 7, 8]})
 
# Verificar valores faltantes
print(df.isnull())
#       A     B
# 0  False False
# 1  False  True
# 2   True False
# 3  False False

En el ejemplo anterior, el método df.isnull() devuelve un DataFrame booleano que indica la presencia de valores faltantes en cada celda.

Comprendiendo la diferencia entre pandas.isnull() y pandas.isna()

Las funciones pandas.isnull() y pandas.isna() son prácticamente iguales y se pueden usar indistintamente. Ambas funciones cumplen el mismo propósito de identificar valores faltantes en un DataFrame o Serie.

La principal diferencia es que pandas.isna() es una forma más moderna y recomendada de verificar valores faltantes, ya que ofrece un mejor soporte para manejar diferentes tipos de datos, incluidos los valores NaN de NumPy, None de Python y los indicadores de valores faltantes propios de Pandas.

En la mayoría de los casos, puedes usar pandas.isna() en lugar de pandas.isnull() sin ningún problema. Sin embargo, si necesitas mantener la compatibilidad con versiones anteriores de Pandas, es posible que necesites usar pandas.isnull().

Manejo de datos faltantes con pandas is nan

Una vez que has identificado los valores faltantes usando pandas.isnull() o pandas.isna(), puedes usar varios métodos para manejarlos. Algunas técnicas comunes incluyen:

  1. Reemplazar valores faltantes: Puedes reemplazar los valores faltantes con un valor específico o un valor calculado en función de los datos.
df['A'] = df['A'].fillna(0)  # Reemplazar valores faltantes en la columna 'A' con 0
  1. Eliminar filas o columnas con valores faltantes:
df = df.dropna(subset=['A', 'B'])  # Eliminar filas con valores faltantes en las columnas 'A' o 'B'
  1. Imputar valores faltantes: Puedes utilizar varias técnicas de imputación, como imputación de media, mediana o moda, para llenar los valores faltantes.
from sklearn.impute import SimpleImputer
imputer = SimpleImputer(strategy='mean')
df[['A', 'B']] = imputer.fit_transform(df[['A', 'B']])
  1. Interpolar valores faltantes: Para datos de series de tiempo, puedes usar la interpolación para estimar los valores faltantes en función de los puntos de datos circundantes.
df = df.interpolate()  # Interpolar valores faltantes en el DataFrame

Aplicando pandas.isnull() y pandas.isna() en la manipulación de datos

Identificación de valores faltantes en un DataFrame

Puedes utilizar las funciones pandas.isnull() o pandas.isna() para identificar valores faltantes en un DataFrame:

import pandas as pd
 
# Crear un DataFrame de muestra
df = pd.DataFrame({'A': [1, 2, None, 4], 'B': [5, None, 7, 8]})
 
# Verificar valores faltantes
print(df.isnull())
#       A     B
# 0  False False
# 1  False  True
# 2   True False
# 3  False False

El DataFrame booleano resultante indica la presencia de valores faltantes en cada celda.

Manejo de valores faltantes utilizando pandas.isnull() y pandas.isna()

Puedes utilizar la máscara booleana devuelta por pandas.isnull() o pandas.isna() para realizar diversas operaciones en el DataFrame, como:

  1. Reemplazar valores faltantes:
df['A'] = df['A'].fillna(0)
df['B'] = df['B'].fillna(df['B'].mean())
  1. Eliminar filas o columnas con valores faltantes:
df = df.dropna(subset=['A', 'B'])  # Eliminar filas con valores faltantes en las columnas 'A' o 'B'
df = df.dropna(how='all')  # Eliminar filas con todos los valores faltantes
df = df.dropna(axis=1)  # Eliminar columnas con valores faltantes
  1. Imputar valores faltantes:
from sklearn.impute import SimpleImputer
imputer = SimpleImputer(strategy='mean')
df[['A', 'B']] = imputer.fit_transform(df[['A', 'B']])

Reemplazar valores faltantes con un valor específico

Puedes reemplazar valores faltantes con un valor específico utilizando el método fillna():

# Reemplazar valores faltantes en la columna 'A' con 0
df['A'] = df['A'].fillna(0)
 
# Reemplazar valores faltantes en la columna 'B' con la media de la columna
df['B'] = df['B'].fillna(df['B'].mean())

Eliminar filas o columnas con valores faltantes

Puedes eliminar filas o columnas con valores faltantes utilizando el método dropna():

# Eliminar filas con valores faltantes en las columnas 'A' o 'B'
df = df.dropna(subset=['A', 'B'])
 
# Eliminar filas con todos los valores faltantes
df = df.dropna(how='all')
 
# Eliminar columnas con valores faltantes
df = df.dropna(axis=1)

Técnicas avanzadas con pandas is nan

Combinar pandas.isnull() y pandas.isna() con otros métodos de DataFrame

Puedes combinar las funciones pandas.isnull() o pandas.isna() con otros métodos de DataFrame para realizar operaciones más complejas. Por ejemplo, puedes usarlos en filtrado condicional, transformación de datos y más.

# Filtrar filas con valores faltantes en la columna 'A'
filtered_df = df[df['A'].isnull()]
 
# Llenar valores faltantes en la columna 'B' con la mediana de los valores no faltantes en esa columna
df['B'] = df['B'].fillna(df['B'].median())
 
# Crear una nueva columna que indique la presencia de valores faltantes en la columna 'A'
df['has_missing_A'] = df['A'].isnull()

Filtrado condicional basado en valores faltantes

Puedes usar la máscara booleana devuelta por pandas.isnull() o pandas.isna() para realizar un filtrado condicional en tu DataFrame:

# Filtrar filas con valores faltantes en la columna 'A'
filtered_df = df[df['A'].isnull()]
 
# Filtrar filas con valores no faltantes en la columna 'B'
non_missing_df = df[~df['B'].isnull()]

Imputación de valores faltantes usando varias técnicas

Además de la simple sustitución de valores, puedes utilizar técnicas más avanzadas para imputar valores faltantes, como:

  1. Imputación de media/mediana/moda:
from sklearn.impute import SimpleImputer
imputer = SimpleImputer(strategy='mean')
df[['A', 'B']] = imputer.fit_transform(df[['A', 'B']])
  1. Imputación KNN:
from fancyimpute import KNNImputer
imputer = KNNImputer(n_neighbors=5)
df[['A', 'B']] = imputer.fit_transform(df[['A', 'B']])
  1. Imputación iterativa:
from sklearn.experimental import enable_iterative_imputer
from sklearn.impute import IterativeImputer
imputer = IterativeImputer()
df[['A', 'B']] = imputer.fit_transform(df[['A', 'B']])

Estas técnicas avanzadas de imputación pueden ser particularmente útiles al tratar con patrones de datos faltantes más complejos o características interdependientes.

Explorando casos de uso específicos para pandas is nan

Limpieza y preprocesamiento de datos con pandas is nan

Uno de los casos de uso principales para pandas.isnull() y pandas.isna() es en la etapa de limpieza y preprocesamiento de datos de un análisis de datos o de un flujo de trabajo de aprendizaje automático. Estas funciones pueden ayudarte a identificar y manejar los valores faltantes, lo cual es un paso crucial para garantizar la calidad y confiabilidad de tus datos.

Aquí tienes un ejemplo de cómo puedes usar pandas.isna() para limpiar y preprocesar un conjunto de datos:

import pandas as pd
 
# Cargar el conjunto de datos
df = pd.read_csv('dataset.csv')
 
# Identificar valores faltantes
missing_values = df.isna().sum()
print(missing_values)
 
# Eliminar filas con valores faltantes en cualquier columna
df = df.dropna()
 
# Rellenar valores faltantes en la columna 'edad' con la mediana
df['edad'] = df['edad'].fillna(df['edad'].median())
 
# Crear una nueva columna que indique la presencia de valores faltantes en la columna 'ingresos'
df['tiene_ingreso_faltante'] = df['ingresos'].isna()

En este ejemplo, primero identificamos el número de valores faltantes en cada columna usando df.isna().sum(). Luego eliminamos las filas con valores faltantes en cualquier columna y llenamos los valores faltantes en la columna 'edad' con la mediana. Finalmente, creamos una nueva columna que indica la presencia de valores faltantes en la columna 'ingresos'.

Manejo de valores faltantes en datos de series de tiempo

Al trabajar con datos de series de tiempo, el manejo de valores faltantes puede ser particularmente desafiante. pandas.isnull() y pandas.isna() se pueden combinar con otras funciones específicas para series de tiempo para manejar valores faltantes en estos conjuntos de datos.

import pandas as pd
 
# Crear un DataFrame de series de tiempo de ejemplo
df = pd.DataFrame({'A': [1, 2, None, 4, 5], 'B': [5, None, 7, 8, 9]},
                  index=pd.date_range('2022-01-01', periods=5, freq='D'))
 
# Identificar valores faltantes
print(df.isna())
#             A     B
# 2022-01-01 False False
# 2022-01-02 False  True
# 2022-01-03  True False
# 2022-01-04 False False
# 2022-01-05 False False
 
# Interpolar valores faltantes
df = df.interpolate()
print(df)
#             A    B
# 2022-01-01  1  5.0
# 2022-01-02  2  6.0
# 2022-01-03  3  7.0
# 2022-01-04  4  8.0
# 2022-01-05  5  9.0

En este ejemplo, creamos un DataFrame de series de tiempo de ejemplo con valores faltantes. Luego utilizamos el método interpolate() para estimar los valores faltantes en función de los puntos de datos circundantes.

Manejo de valores faltantes en modelos de aprendizaje automático

Los valores faltantes pueden tener un impacto significativo en el rendimiento de los modelos de aprendizaje automático. pandas.isnull() y pandas.isna() se pueden utilizar para identificar y manejar los valores faltantes antes de alimentar los datos a un modelo de aprendizaje automático.

import pandas as pd
from sklearn.impute import SimpleImputer
from sklearn.linear_model import LinearRegression
 
# Cargar el conjunto de datos
df = pd.read_csv('dataset.csv')
 
# Identificar valores faltantes
missing_values = df.isna().sum()
print(missing_values)
 
# Imputar valores faltantes utilizando imputación por media
imputer = SimpleImputer(strategy='mean')
X = imputer.fit_transform(df.drop('target', axis=1))
y = df['target']
 
# Entrenar un modelo de regresión lineal
model = LinearRegression()
model.fit(X, y)

En este ejemplo, primero identificamos los valores faltantes en el conjunto de datos usando df.isna().sum(). Luego utilizamos SimpleImputer de scikit-learn para imputar los valores faltantes utilizando la media de cada característica. Finalmente, entrenamos un modelo de regresión lineal con los datos imputados.

El manejo de valores faltantes es un paso crítico en la preparación de datos para modelos de aprendizaje automático, ya que muchos modelos no pueden manejar valores faltantes directamente. Al utilizar pandas.isnull() y pandas.isna(), puedes asegurarte

Funciones

Las funciones son bloques de código reutilizables que realizan una tarea específica. Pueden aceptar entradas, realizar operaciones y devolver salidas. Las funciones ayudan a organizar y modularizar tu código, haciéndolo más legible y mantenible.

Aquí tienes un ejemplo de una función simple que calcula el área de un rectángulo:

def calcular_area(longitud, ancho):
    """
    Calcula el área de un rectángulo.
 
    Args:
        longitud (float): La longitud del rectángulo.
        ancho (float): El ancho del rectángulo.
 
    Returns:
        float: El área del rectángulo.
    """
    area = longitud * ancho
    return area
 
# Uso
longitud_rectangulo = 5.0
ancho_rectangulo = 3.0
area_rectangulo = calcular_area(longitud_rectangulo, ancho_rectangulo)
print(f"El área del rectángulo es de {area_rectangulo} unidades cuadradas.")

En este ejemplo, la función calcular_area toma dos parámetros, longitud y ancho, y devuelve el área calculada. La función también incluye una cadena de documentación que proporciona una breve descripción de la función y los parámetros y el valor de retorno esperados.

Módulos y paquetes

La biblioteca estándar de Python proporciona una amplia gama de módulos integrados, que son colecciones de funciones, clases y variables. También puedes crear tus propios módulos y paquetes para organizar tu código y hacerlo más reutilizable.

Aquí tienes un ejemplo de cómo crear un módulo simple:

# my_module.py
def greet(name):
    """
    Saluda a la persona con el nombre dado.
 
    Args:
        name (str): El nombre de la persona a saludar.
 
    Returns:
        str: El mensaje de saludo.
    """
    return f"Hola, {name}!"

Para usar el módulo, puedes importarlo en otro archivo de Python:

# main.py
import my_module
 
saludo = my_module.greet("Alice")
print(saludo)  # Salida: ¡Hola, Alice!

Los paquetes son colecciones de módulos que se organizan en directorios. Te permiten agrupar módulos relacionados y proporcionar una estructura jerárquica para tu código. Aquí tienes un ejemplo de cómo crear un paquete simple:

mi_paquete/
    __init__.py
    utils/
        __init__.py
        math_functions.py
        string_functions.py

Los archivos __init__.py se utilizan para definir la estructura del paquete y especificar qué módulos se deben importar cuando se importa el paquete.

# mi_paquete/utils/math_functions.py
def suma(a, b):
    return a + b
 
def resta(a, b):
    return a - b
# main.py
from mi_paquete.utils import math_functions
 
resultado = math_functions.suma(5, 3)
print(resultado)  # Salida: 8

Excepciones

Las excepciones son eventos que ocurren durante la ejecución de un programa y que interrumpen el flujo normal de las instrucciones del programa. Python tiene un mecanismo de manejo de excepciones integrado que te permite manejar y gestionar estas situaciones inesperadas.

Aquí tienes un ejemplo de cómo manejar una excepción ZeroDivisionError:

def dividir(a, b):
    try:
        resultado = a / b
        return resultado
    except ZeroDivisionError:
        print("Error: División por cero.")
        return None
 
print(dividir(10, 2))  # Salida: 5.0
print(dividir(10, 0))  # Salida: Error: División por cero.

En este ejemplo, la función dividir intenta dividir el primer argumento por el segundo argumento. Si se produce un ZeroDivisionError, la función captura la excepción e imprime un mensaje de error, luego devuelve None.

También puedes crear excepciones personalizadas definiendo tus propias clases de excepción que heredan de la clase integrada Exception o una de sus subclases.

class ErrorValorNegativo(Exception):
    """Se lanza cuando se encuentra un valor negativo."""
    pass
 
def calcular_raiz_cuadrada(numero):
    if numero < 0:
        raise ErrorValorNegativo("No se puede calcular la raíz cuadrada de un número negativo.")
    return numero ** 0.5
 
try:
    print(calcular_raiz_cuadrada(16))  # Salida: 4.0
    print(calcular_raiz_cuadrada(-4))
except ErrorValorNegativo as e:
    print(e)  # Salida: No se puede calcular la raíz cuadrada de un número negativo.

En este ejemplo, la función calcular_raiz_cuadrada plantea una excepción personalizada ErrorValorNegativo si el número de entrada es negativo. Luego, la excepción se captura y se maneja en el bloque try-except.

Entrada/Salida de archivos

Python proporciona funciones y métodos integrados para leer y escribir archivos. La forma más común de trabajar con archivos es utilizando la función open(), que devuelve un objeto de archivo que puede utilizarse para realizar diversas operaciones de archivo.

Aquí tienes un ejemplo de cómo leer y escribir en un archivo:

# Escribir en un archivo
with open("ejemplo.txt", "w") as archivo:
    archivo.write("Esta es la primera línea.\n")
    archivo.write("Esta es la segunda línea.\n")
 
# Leer desde un archivo
with open("ejemplo.txt", "r") as archivo:
    contenido = archivo.read()
    print(contenido)
    # Salida:
    # Esta es la primera línea.
    # Esta es la segunda línea.

En este ejemplo, la función open() se utiliza para abrir un archivo llamado "ejemplo.txt" en modo de escritura ("w") y escribir dos líneas de texto en él. Luego, se abre el archivo en modo de lectura ("r") y se leen e imprimen los contenidos.

La instrucción with se utiliza para asegurarse de que el archivo se cierre correctamente después de completar las operaciones, incluso si se produce una excepción.

También puedes leer archivos línea por línea utilizando un bucle for:

with open("ejemplo.txt", "r") as archivo:
    for linea in archivo:
        print(linea.strip())
    # Salida:
    # Esta es la primera línea.
    # Esta es la segunda línea.

En este ejemplo, se utiliza el método strip() para eliminar el carácter de nueva línea de cada línea.

Expresiones regulares

Las expresiones regulares (regex) son una herramienta poderosa para la búsqueda de patrones y la manipulación de texto. El módulo re integrado de Python proporciona un conjunto completo de funciones y métodos para trabajar con expresiones regulares.

Aquí tienes un ejemplo de cómo utilizar expresiones regulares para validar una dirección de correo electrónico:

import re
 
def es_correo_valido(correo):
    """
    Comprueba si la dirección de correo electrónico dada es válida.
 
    Args:
        correo (str): La dirección de correo electrónico a validar.
 
    Returns:
        bool: True si la dirección de correo electrónico es válida, False en caso contrario.
    """
    patron = r'^[\w\.-]+@[\w\.-]+\.\w+$'
    if re.match(patron, correo):
        return True
    else:
        return False
 
print(es_correo_valido("ejemplo@ejemplo.com"))  # Salida: True
print(es_correo_valido("correo_invalido"))  # Salida: False

En este ejemplo, la función es_correo_valido toma una dirección de correo electrónico como entrada y utiliza un patrón de expresión regular para verificar si la dirección de correo electrónico es válida. La función re.match() se utiliza para aplicar el patrón a la dirección de correo electrónico y devolver un resultado booleano.

Las expresiones regulares se pueden utilizar para una amplia gama de tareas de procesamiento de texto, como:

  • Buscar patrones específicos en el texto
  • Extraer información del texto
  • Reemplazar o modificar el texto en función de patrones
  • Validar datos de entrada Mientras que las expresiones regulares pueden ser poderosas, también pueden volverse complejas y difíciles de leer, especialmente para casos de uso más avanzados. Es importante equilibrar el uso de expresiones regulares con otras técnicas de procesamiento de texto, como la manipulación de cadenas y los métodos de cadena incorporados.

Conclusión

En este tutorial, has aprendido sobre varios conceptos de nivel intermedio de Python, incluyendo funciones, módulos y paquetes, manejo de excepciones, E/S de archivos y expresiones regulares. Estos temas son esenciales para construir aplicaciones de Python más complejas y robustas.

Recuerda, la mejor manera de mejorar tus habilidades en Python es practicar, experimentar y aprender continuamente. Explora la biblioteca estándar de Python, lee la documentación y participa en comunidades en línea para ampliar tus conocimientos y mantenerte actualizado con los últimos avances en el ecosistema de Python.

¡Feliz codificación!

MoeNagy Dev