TitanicXD / app.py
aplaneUBO's picture
Upload 7 files
5cf113c verified
Raw
History Blame Contribute Delete
4.45 kB
# =========================================================
# Predicción de Supervivencia en el Titanic — Demo Gradio
# Pensada para desplegarse en Hugging Face Spaces.
#
# La interfaz pregunta en "idioma humano" (Sexo, Puerto de
# embarque, Clase del pasaje...) y la app traduce internamente
# esas respuestas a las columnas one-hot que espera el modelo.
# =========================================================
import json
import pickle
import pandas as pd
import gradio as gr
# -------------------------------------------------------
# 1. Cargar modelo y archivos auxiliares
# -------------------------------------------------------
with open("model_rf.pkl", "rb") as f:
model = pickle.load(f)
# Orden exacto de columnas usado en el entrenamiento
with open("model_columns.json", "r") as f:
MODEL_COLUMNS = json.load(f)
# Rangos min-max (post-limpieza) para los sliders
with open("ranges.json", "r") as f:
RANGES = json.load(f)
# -------------------------------------------------------
# 2. Función de predicción
# -------------------------------------------------------
def predecir(clase, edad, hermanos, padres_hijos, tarifa, sexo, puerto):
"""Recibe los valores 'humanos' de la interfaz, los traduce a las
columnas one-hot del modelo y devuelve las probabilidades."""
# Traducción interfaz → columnas del modelo
fila = {
"Clase": int(clase[0]), # "1ª clase" → 1
"Edad": edad,
"HermanosConyuge": hermanos,
"PadresHijos": padres_hijos,
"Tarifa": tarifa,
"Sexo_mujer": 1 if sexo == "Mujer" else 0,
"PuertoEmbarque_Queenstown": 1 if puerto.startswith("Queenstown") else 0,
"PuertoEmbarque_Southampton": 1 if puerto.startswith("Southampton") else 0,
# Cherbourg es la categoría base (drop_first): ambas dummies en 0
}
# Reconstruir el vector en el MISMO orden del entrenamiento
x = pd.DataFrame([fila], columns=MODEL_COLUMNS)
prob_sobrevive = float(model.predict_proba(x)[0][1])
# gr.Label muestra esto como barras de probabilidad
return {
"Sobrevive 🟢": prob_sobrevive,
"No sobrevive 🔴": 1 - prob_sobrevive,
}
# -------------------------------------------------------
# 3. Construcción de la interfaz
# -------------------------------------------------------
entradas = [
gr.Radio(
choices=["1ª clase", "2ª clase", "3ª clase"],
value="3ª clase",
label="Clase del pasaje",
info="1ª = la más cara, 3ª = la más económica",
),
gr.Slider(
RANGES["Edad"]["min"], RANGES["Edad"]["max"], value=28, step=1,
label="Edad (años)",
),
gr.Slider(
RANGES["HermanosConyuge"]["min"], RANGES["HermanosConyuge"]["max"], value=0, step=1,
label="Hermanos/as o cónyuge a bordo",
),
gr.Slider(
RANGES["PadresHijos"]["min"], RANGES["PadresHijos"]["max"], value=0, step=1,
label="Padres o hijos a bordo",
),
gr.Slider(
RANGES["Tarifa"]["min"], RANGES["Tarifa"]["max"], value=15, step=0.5,
label="Tarifa pagada (libras de 1912)",
),
gr.Radio(
choices=["Mujer", "Hombre"],
value="Mujer",
label="Sexo",
),
gr.Radio(
choices=["Cherbourg (Francia)", "Queenstown (Irlanda)", "Southampton (Inglaterra)"],
value="Southampton (Inglaterra)",
label="Puerto de embarque",
),
]
app = gr.Interface(
fn=predecir,
inputs=entradas,
outputs=gr.Label(num_top_classes=2, label="Predicción"),
title="🚢 Predicción de Supervivencia en el Titanic",
description=(
"Modelo **Random Forest** entrenado con el dataset clásico del Titanic. "
"Ajusta las características del pasajero y el modelo estimará su "
"probabilidad de supervivencia.\n\n"
"*Pipeline sin data leakage: imputación, outliers y escalado "
"calculados solo con el set de entrenamiento.*"
),
examples=[
["1ª clase", 35, 1, 0, 53.0, "Mujer", "Cherbourg (Francia)"],
["3ª clase", 25, 0, 0, 7.5, "Hombre", "Southampton (Inglaterra)"],
["2ª clase", 8, 1, 2, 26.0, "Hombre", "Southampton (Inglaterra)"],
],
flagging_mode="never",
)
# -------------------------------------------------------
# 4. Ejecutar la aplicación
# -------------------------------------------------------
if __name__ == "__main__":
app.launch()