Saltar al contenido

# manejo-de-datos-en-pandas

Manejo de datos en Pandas

Volver a la portada del curso
Notebook

Implementación del análisis de datos

Sección 6 · Proyecto Final

Implementación del análisis de datos

Esta lección junta todo el curso en un solo flujo: del texto crudo del CSV de las sucursales de PyShop a un reporte con indicadores, tablas, gráficas y conclusiones. El notebook analisis-pedidos lo implementa completo, y cada paso es una función, de modo que el mismo notebook sirve para el archivo del año siguiente. Es el modelo del proyecto final: allí se repite el recorrido con un archivo nuevo.

1. Reporte de calidad: antes y después

El análisis empieza midiendo. La función reporte_calidad(df) devuelve un diccionario con filas, filas duplicadas, identificadores repetidos, ciudades distintas, tipo del precio, fechas que no se pueden convertir y nulos por columna. Se aplica al crudo y al limpio, y las dos columnas se comparan en un DataFrame:

IndicadorAntesDespués
filas1025991
duplicadas250
ciudades distintas165
tipo de preciostrfloat64
nulos de cantidad / precio43 / 210 / 0
fechas inválidas90
nulos de calificación383369

Las fechas inválidas no son nulos en el crudo, porque ahí la fecha es texto: el reporte las cuenta intentando convertirlas con errors="coerce". La calificación conserva nulos a propósito: es un faltante estructural.

2. Limpiar y validar

La limpieza es la función limpiar(texto) de la lección anterior: una cadena de métodos con drop_duplicates, dos assign con lambda, dropna(subset=["fecha"]) y el cálculo del total. Después, validar(df) comprueba con assert que pedido_id sea único, que haya exactamente cinco ciudades, que cantidad, precio, fecha y total no tengan nulos y que todos los totales sean positivos. Si una condición falla, el notebook se detiene con un mensaje claro.

3. KPIs

Para medir ingreso se excluyen los cancelados. Seis indicadores resumen el año:

val = pedidos[pedidos["estado"] != "cancelado"]
kpis = {
    "pedidos válidos": len(val),               # 906
    "ingreso": val["total"].sum(),             # 1,350,460
    "ticket medio": val["total"].mean(),       # 1,490.57
    "cancelación %": (pedidos["estado"] == "cancelado").mean() * 100,
    "clientes": val["cliente"].nunique(),      # 321
}

La tasa de cancelación general es 8.6 %. La media de una columna booleana es una proporción: es la forma más corta de calcular una tasa.

4. Preguntas de negocio

Cada pregunta se responde con una agrupación:

  • ¿Qué categoría genera más ingreso? Electrónica aporta el 59.0 %; Libros, el 4.9 %.
  • ¿Cómo se comparan las ciudades? Con agg con nombres (pedidos, ingreso, ticket y calificación): Ciudad de México lidera con 377 pedidos y 523,378 MXN, pero su ticket medio (1,388.27) es el más bajo; el de Puebla (1,736.11) es el más alto.
  • ¿Qué ciudad cancela más? Puebla (11.2 %) y Monterrey (10.8 %); las demás están entre 7.6 % y 7.8 %.
  • ¿Qué se vende más? Por unidades: Sartén antiadherente (160), Juego de toallas (154) y Libro de Python (145). El cliente que más gastó (C0348) suma 33,033 MXN.
  • ¿Cómo se reparte el año? El mes máximo es febrero (148,298) y el mínimo mayo (71,553).

5. Gráficas del reporte

Una figura de 2 × 2 creada con plt.subplots reúne el ranking de categorías (barh), el ingreso mensual (line con el eje desde cero), la tasa de cancelación por ciudad (barh) y la distribución del total por pedido (hist con 20 intervalos). Cada .plot recibe su panel con ax=axs[fila, columna], y fig.suptitle pone el título general.

6. Conclusiones

El notebook cierra con conclusiones de una o dos líneas, cada una con su cifra: la calidad del archivo, la concentración en Electrónica, el contraste entre volumen y ticket por ciudad y la cancelación de Puebla y Monterrey. Incluye también lo que los datos no muestran: el ingreso mensual sube y baja, pero estos datos sintéticos no modelan estacionalidad, así que no hay base para hablar de temporadas; y las calificaciones medias por ciudad (3.94 a 4.07) son casi iguales. Reportar lo que no se encontró evita que alguien tome decisiones sobre ruido.

7. Guardar y comprobar

pedidos.to_csv("pedidos_limpios.csv", index=False)
releido = pd.read_csv("pedidos_limpios.csv",
                      parse_dates=["fecha"])
print(releido.shape, releido["fecha"].dtype)
# (991, 11) datetime64[us]

El archivo se guarda en la carpeta de trabajo del notebook. Releerlo y comparar forma, tipos e ingreso confirma que no se perdió nada en el camino.

8. Ejercicios

Cuatro funciones con pruebas: los KPIs básicos, la participación de cada categoría en el ingreso, el resumen mensual y una versión de validar que además exige que todas las fechas sean de 2025. Las soluciones están al final.

En qué fijarse

  • La misma función de calidad, antes y después, documenta la limpieza mejor que cualquier párrafo.
  • Excluir los cancelados es una decisión: escríbela donde se calcula el ingreso.
  • Compara promedios cuando los grupos tienen distinto tamaño.
  • Cada conclusión lleva una cifra; ninguna lleva una causa que los datos no respaldan.

Recursos