Regresión Logística Binaria Múltiple en R
29-07-2024
Un modelo de regresión logística binaria múltiple es una técnica estadística utilizada para predecir la probabilidad de un resultado binario (dos posibles resultados, como “sí” o “no”, “1” o “0”) basado en uno o más predictores, que pueden ser variables continuas o categóricas.
Variable Dependiente Binaria: El resultado que se predice es una variable binaria, es decir, tiene dos categorías.
Variables Independientes: Puede incluir múltiples variables independientes (predictores) que pueden ser tanto continuas como categóricas.
Función Logística: Utiliza la función logística para modelar la probabilidad de que ocurra un evento. La salida del modelo es la probabilidad de que la variable dependiente tome un valor específico (por ejemplo, “1”).
NOTA
El contenido del documento, define los pasos para la construcción de un modelo de Regresión Logística Binaria Múltiple e incluye la debida interpretación del código que se presenta, en relación con la estructura en R.
La base de datos con la que se trabajará en este documento, es de tipo .csv y para poder acceder a ella se necesita la librería readr. Este paquete está diseñado para facilitar la importación y exportación de datos en R, especialmente para archivos de texto, como CSV y TSV.
library(readr)
misdatos <- read_csv("heart_failure_clinical_records_dataset.csv")
class(misdatos)
## [1] "spec_tbl_df" "tbl_df" "tbl" "data.frame"
Para asegurar la compatibilidad y funcionalidad con diversas funciones y paquetes de R, los datos se deben transformar a Data.Frame.
misdatos = as.data.frame(misdatos)
str(misdatos)
## 'data.frame': 299 obs. of 13 variables:
## $ age : num 75 55 65 50 65 90 75 60 65 80 ...
## $ anaemia : num 0 0 0 1 1 1 1 1 0 1 ...
## $ creatinine_phosphokinase: num 582 7861 146 111 160 ...
## $ diabetes : num 0 0 0 0 1 0 0 1 0 0 ...
## $ ejection_fraction : num 20 38 20 20 20 40 15 60 65 35 ...
## $ high_blood_pressure : num 1 0 0 0 0 1 0 0 0 1 ...
## $ platelets : num 265000 263358 162000 210000 327000 ...
## $ serum_creatinine : num 1.9 1.1 1.3 1.9 2.7 2.1 1.2 1.1 1.5 9.4 ...
## $ serum_sodium : num 130 136 129 137 116 132 137 131 138 133 ...
## $ sex : num 1 1 1 1 0 1 1 1 0 1 ...
## $ smoking : num 0 0 1 0 0 1 0 1 0 1 ...
## $ time : num 4 6 7 7 8 8 10 10 10 10 ...
## $ DEATH_EVENT : num 1 1 1 1 1 1 1 1 1 1 ...
En la salida anterior se puede observar que la base de datos contiene 13 variables y 299 filas, ademas los datos ya están en formato Data.Frame por lo que se puede continuar trabajando. Para comenzar se obtendrá la visualización de las primeras filas de la base de datos.
head(misdatos,5)
| age | anaemia | creatinine_phosphokinase | diabetes | ejection_fraction | high_blood_pressure | platelets | serum_creatinine | serum_sodium | sex | smoking | time | DEATH_EVENT |
|---|---|---|---|---|---|---|---|---|---|---|---|---|
| 75 | 0 | 582 | 0 | 20 | 1 | 265000 | 1.9 | 130 | 1 | 0 | 4 | 1 |
| 55 | 0 | 7861 | 0 | 38 | 0 | 263358 | 1.1 | 136 | 1 | 0 | 6 | 1 |
| 65 | 0 | 146 | 0 | 20 | 0 | 162000 | 1.3 | 129 | 1 | 1 | 7 | 1 |
| 50 | 1 | 111 | 0 | 20 | 0 | 210000 | 1.9 | 137 | 1 | 0 | 7 | 1 |
| 65 | 1 | 160 | 1 | 20 | 0 | 327000 | 2.7 | 116 | 0 | 0 | 8 | 1 |
names(misdatos)
| Variable | Tipo | Descripción | Categorías |
|---|---|---|---|
| age | Numérica | Edad del paciente |
|
| anaemia | Categórica | Presencia de anemia | 0 = El paciente no tiene anemia 1 = El paciente tiene anemia |
| creatinine_phosphokinase | Numérica | Niveles de creatina fosfoquinasa en la sangre |
|
| diabetes | Categórica | Indicador de si el paciente tiene diabetes | 0 = Ausencia de diabetes 1 = Presencia de diabetes |
| ejection_fraction | Numérica | Cantidad de sangre que el ventrículo izquierdo expulsa con cada contracción (Indicador de la función cardíaca) |
|
| high_blood_pressure | Categórica | Indicador de hipertensión arterial | 0 = Ausencia de hipertensión 1 = Presencia de hipertensión |
| platelets | Numérica | Recuento de plaquetas en la sangre |
|
| serum_creatinine | Numérica | Nivel de creatinina en suero (Indicador de la función renal) |
|
| serum_sodium | Numérica | Nivel de sodio en suero |
|
| sex | Categórica | Género del paciente | 0 = Masculino 1 = Femenino |
| smoking | Categórica | Indicador de si el paciente es fumador | 0 = No fuma 1 = Si fuma |
| time | Numérica | Días de ingreso que tiene el paciente |
|
| DEATH_EVENT | Categórica | Indicador de evento de muerte | 0 = No muerte del paciente 1 = Muerte del paciente |
Ahora se establecerá una semilla para el generador de números aleatorios en R. Esto es importante para garantizar que los resultados sean reproducibles, esto significa que si alguien más ejecuta el mismo código con la misma semilla, obtendrá los mismos resultados, especialmente en procesos que involucran aleatoriedad, como la selección de muestras. Para establecer la semilla se usara el siguiente código:
set.seed(2021)
Una vez establecida la semilla se determinará el tamaño de la base de datos con la que se esta trabajando:
n = nrow(misdatos)
n
## [1] 299
Se tienen 299 filas en la base. Ahora que se conoce el número de filas, se puede proceder a dividir la base de datos en un conjunto de entrenamiento y un conjunto de datos de prueba. Para realizar dicha partición se debe generar una muestra aleatoria de índices (números de filas) que representan el \(70\%\) del conjunto de datos total para poder generar el conjunto de datos de entrenamiento:
d_ind = sample(n,n*0.70)
Una vez creado los indices se realiza la partición en los datos de la base original:
records=misdatos[d_ind,]
El código anterior crea el subconjunto de entrenamiento records, que contiene el 70% de las observaciones seleccionadas aleatoriamente de la base misdatos usando los índices generados en d_ind. Además, se debe crear la partición de prueba:
d_test=misdatos[-d_ind,]
El código anterior crea el subconjunto de prueba d_test, que contiene el 30% restante de las observaciones que no fueron seleccionadas para el conjunto de entrenamiento. Para verificar que las variables seleccionadas sean las correctas se leerán los nombres de las variables de la partición de entrenamiento (records).
names(records)
| Variable |
|---|
| age |
| anaemia |
| creatinine_phosphokinase |
| diabetes |
| ejection_fraction |
| high_blood_pressure |
| platelets |
| serum_creatinine |
| serum_sodium |
| sex |
| smoking |
| time |
| DEATH_EVENT |
Se puede observar que son las mismas variables de la base de datos originales. Ahora se calculará la matriz de correlación para las variables seleccionadas del subconjunto de entrenamiento. Esto ayudará a identificar si hay multicolinealidad entre las variables predictoras, lo cual puede afectar la estabilidad y la interpretación del modelo de regresión.
cor(records[c(1,3,5,7,8,9)])
| age | creatinine_phosphokinase | ejection_fraction | platelets | serum_creatinine | serum_sodium | |
|---|---|---|---|---|---|---|
| age | 1.0000000 | -0.0187324 | 0.0256468 | -0.1097173 | 0.1356862 | -0.0726885 |
| creatinine_phosphokinase | -0.0187324 | 1.0000000 | -0.0080132 | -0.0020113 | 0.0541629 | 0.0727306 |
| ejection_fraction | 0.0256468 | -0.0080132 | 1.0000000 | 0.0413740 | 0.0517453 | 0.1013551 |
| platelets | -0.1097173 | -0.0020113 | 0.0413740 | 1.0000000 | -0.0873660 | 0.0705143 |
| serum_creatinine | 0.1356862 | 0.0541629 | 0.0517453 | -0.0873660 | 1.0000000 | -0.1412220 |
| serum_sodium | -0.0726885 | 0.0727306 | 0.1013551 | 0.0705143 | -0.1412220 | 1.0000000 |
La multicolinealidad ocurre cuando dos o más variables predictoras en un modelo de regresión están altamente correlacionadas entre sí. En el resultado anterior se puede apreciar que la mayoría de las variables no tienen una correlación alta, ya que los valores no sobrepasan el \(|0.14|\). Esto es justo lo que se necesita para poder obtener un modelo de regresión logística múltiple adecuado.
La construcción del modelo se realizará con la librería MASS. La variable respuesta que se utilizará será DEATH_EVENT que representa la muerte de un paciente, donde \(1\) representa cuando el paciente muere y \(0\) significa que el paciente no muere.
library(MASS)
my_model=glm(data = records,DEATH_EVENT~.,
family = binomial())
summary(my_model)
##
## Call:
## glm(formula = DEATH_EVENT ~ ., family = binomial(), data = records)
##
## Coefficients:
## Estimate Std. Error z value Pr(>|z|)
## (Intercept) 1.102e+01 7.542e+00 1.461 0.14410
## age 5.624e-02 1.927e-02 2.918 0.00352 **
## anaemia 4.698e-01 4.160e-01 1.129 0.25874
## creatinine_phosphokinase 4.584e-04 3.483e-04 1.316 0.18807
## diabetes 1.068e-01 4.252e-01 0.251 0.80174
## ejection_fraction -7.459e-02 1.905e-02 -3.916 9.01e-05 ***
## high_blood_pressure -2.212e-01 4.511e-01 -0.490 0.62391
## platelets -1.896e-06 2.294e-06 -0.826 0.40870
## serum_creatinine 5.489e-01 1.926e-01 2.849 0.00438 **
## serum_sodium -7.284e-02 5.314e-02 -1.371 0.17043
## sex -1.338e+00 5.321e-01 -2.514 0.01195 *
## smoking 2.293e-01 5.223e-01 0.439 0.66061
## time -2.250e-02 3.911e-03 -5.754 8.73e-09 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## (Dispersion parameter for binomial family taken to be 1)
##
## Null deviance: 259.12 on 208 degrees of freedom
## Residual deviance: 153.24 on 196 degrees of freedom
## AIC: 179.24
##
## Number of Fisher Scoring iterations: 6
EL código anterior ajusta un modelo de regresión logística binaria múltiple utilizando el conjunto de datos records. La variable de respuesta es DEATH_EVENT y el símbolo ~. indica que se incluyen todas las demás variables como predictores. La familia binomial() especifica que el modelo es de tipo logístico binario. Mientras que summary proporciona un resumen del modelo ajustado, incluyendo los coeficientes estimados, errores estándar, valores z, y valores p para cada predictor, así como estadísticas de ajuste globales como el AIC.
Los coeficientes estimados (Estimate) indican el cambio esperado en el logaritmo de las probabilidades (log-odds) de DEATH_EVENT por unidad de cambio en la variable predictora, manteniendo constantes las demás variables. Los valores positivos indican un aumento en la probabilidad del evento, mientras que los valores negativos indican una disminución.
Los errores estándar se espera que sean lo más pequeños posibles para poder obtener una estimación más precisa de los coeficientes. En los resultados se puede observar que los errores son muy pequeños por lo que se tiene una buena estimación de los coeficientes.
| Variable | p.valor |
|---|---|
| age | 0.0035200 |
| ejection_fraction | 0.0000901 |
| serum_creatinine | 0.0043800 |
| sex | 0.0119500 |
| time | 0.0000000 |
| Variable | p.valor |
|---|---|
| Intercept | 0.14410 |
| anaemia | 0.25874 |
| creatinine_phosphokinase | 0.18807 |
| diabetes | 0.80174 |
| high_blood_pressure | 0.62391 |
| platelets | 0.40870 |
| serum_sodium | 0.17043 |
| smoking | 0.66061 |
Para la variable age el coeficiente positivo sugiere que a medida que aumenta la edad, la probabilidad de que ocurra el evento de interés (muerte del paciente) también aumenta. Esto indica que la edad es un factor de riesgo para la mortalidad en este grupo de pacientes.
Para la variable ejection_fraction el coeficiente negativo indica que una mayor fracción de eyección se asocia con una menor probabilidad de muerte. La fracción de eyección es un indicador de la función cardíaca, y un valor mayor generalmente se asocia con un mejor estado de salud cardiovascular.
Para la variable serum_creatinin su coeficiente positivo sugiere que niveles más altos de creatinina en suero están asociados con una mayor probabilidad de muerte. Esto es consistente con la comprensión médica de que niveles elevados de creatinina pueden indicar problemas renales o daño, lo que puede ser un factor de riesgo para la mortalidad.
Para la variable sex el coeficiente negativo indicando que, en comparación con el grupo de referencia (\(masculino = 0\)), el grupo codificado con el otro valor (\(femenio = 1\)) tiene una menor probabilidad de morir. Esto podría reflejar diferencias en la supervivencia entre hombres y mujeres en la muestra.
Para la variable time que representa los días de ingreso que tiene el paciente, el coeficiente negativo sugiere que por cada día de ingreso, la probabilidad de muerte disminuye.
La multicolinealidad ocurre cuando dos o más variables predictoras en un modelo de regresión están altamente correlacionadas entre sí. El VIF( ) calcula los Factores de Inflación de la Varianza para cada predictor en el modelo \(my model\). Un VIF alto sugiere que existe multicolinealidad, es decir, que una variable predictora está altamente correlacionada con una o más variables predictoras, lo cual puede inflar las varianzas de los coeficientes estimados y afectar la interpretación del modelo.
library(carData)
library(car)
vif(my_model)
| VIF | |
|---|---|
| age | 1.129135 |
| anaemia | 1.046886 |
| creatinine_phosphokinase | 1.150944 |
| diabetes | 1.077959 |
| ejection_fraction | 1.220016 |
| high_blood_pressure | 1.076420 |
| platelets | 1.059796 |
| serum_creatinine | 1.116415 |
| serum_sodium | 1.096600 |
| sex | 1.624757 |
| smoking | 1.451073 |
| time | 1.269458 |
\(VIF < 5\): Generalmente considerado aceptable, sugiere que no hay una multicolinealidad preocupante.
\(VIF > 5\): Indica una multicolinealidad moderada, lo cual puede ser motivo de preocupación, pero no necesariamente un problema grave.
\(VIF > 10\): Considerado una señal de alerta de multicolinealidad alta, lo que podría invalidar la interpretación de los coeficientes.
Los valores de VIF indican que no hay problemas significativos de multicolinealidad en el modelo. Por lo tanto, los coeficientes de las variables predictoras son relativamente estables y confiables, y las interpretaciones sobre los efectos de cada predictor en el resultado de la regresión logística binaria múltiple no están comprometidas por la multicolinealidad entre las variables predictoras.
La selección de variables es crucial para construir modelos que sean interpretables, precisos y generalizables. En el modelo anterior hay muchas variables que no son significativas, para comenzar a reducir variables no significativas es recomendable iniciar eliminando las 2 variables que tengan el mayor p-valor y dependiendo de los resultados, se puede continuar con la eliminación de variables.
my_model2=glm(data=records,DEATH_EVENT~.-high_blood_pressure-smoking,
family = binomial(link = "logit"))
summary(my_model2)
##
## Call:
## glm(formula = DEATH_EVENT ~ . - high_blood_pressure - smoking,
## family = binomial(link = "logit"), data = records)
##
## Coefficients:
## Estimate Std. Error z value Pr(>|z|)
## (Intercept) 1.043e+01 7.403e+00 1.409 0.15877
## age 5.516e-02 1.918e-02 2.876 0.00403 **
## anaemia 4.404e-01 4.110e-01 1.072 0.28387
## creatinine_phosphokinase 4.491e-04 3.389e-04 1.325 0.18509
## diabetes 8.655e-02 4.237e-01 0.204 0.83815
## ejection_fraction -7.481e-02 1.905e-02 -3.928 8.57e-05 ***
## platelets -1.913e-06 2.283e-06 -0.838 0.40205
## serum_creatinine 5.381e-01 1.888e-01 2.850 0.00437 **
## serum_sodium -6.842e-02 5.201e-02 -1.316 0.18831
## sex -1.197e+00 4.562e-01 -2.624 0.00870 **
## time -2.232e-02 3.887e-03 -5.742 9.35e-09 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## (Dispersion parameter for binomial family taken to be 1)
##
## Null deviance: 259.12 on 208 degrees of freedom
## Residual deviance: 153.64 on 198 degrees of freedom
## AIC: 175.64
##
## Number of Fisher Scoring iterations: 6
En el resultado anterior, se puede observar que las variables significativas son:
El AIC proporciona una medida de la calidad del modelo ajustado. Un AIC más bajo indica un mejor ajuste del modelo, considerando tanto la bondad del ajuste como la complejidad del modelo.
# Modelo original
my_model$aic
# Modelo con las 2 variables eliminadas
my_model2$aic
| Modelo | AIC |
|---|---|
| Modelo Original | 179.2415 |
| Modelo 2 | 175.6393 |
Al comparar el AIC del modelo original y el nuevo modelo con las 2 variables eliminadas, se puede verificar que el nuevo AIC es menor que el del primer modelo. Este AIC significa que el nuevo modelo tiene un mejor ajuste del modelo.
Ahora se procederá a eliminar otras 2 variables que tienen un mayor p-valor para poder obtener un mejor ajuste del modelo.
my_model3=glm(data=records,DEATH_EVENT~.-high_blood_pressure-smoking-platelets-diabetes,
family = binomial(link = "logit"))
summary(my_model3)
##
## Call:
## glm(formula = DEATH_EVENT ~ . - high_blood_pressure - smoking -
## platelets - diabetes, family = binomial(link = "logit"),
## data = records)
##
## Coefficients:
## Estimate Std. Error z value Pr(>|z|)
## (Intercept) 10.1176501 7.2122510 1.403 0.16066
## age 0.0543893 0.0187074 2.907 0.00364 **
## anaemia 0.4637488 0.4101194 1.131 0.25815
## creatinine_phosphokinase 0.0004687 0.0003342 1.403 0.16075
## ejection_fraction -0.0738926 0.0188889 -3.912 9.16e-05 ***
## serum_creatinine 0.5413446 0.1876921 2.884 0.00392 **
## serum_sodium -0.0699922 0.0511068 -1.370 0.17083
## sex -1.1717596 0.4515627 -2.595 0.00946 **
## time -0.0219631 0.0038254 -5.741 9.39e-09 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## (Dispersion parameter for binomial family taken to be 1)
##
## Null deviance: 259.12 on 208 degrees of freedom
## Residual deviance: 154.39 on 200 degrees of freedom
## AIC: 172.39
##
## Number of Fisher Scoring iterations: 6
En el resultado anterior, se puede observar que las variables significativas son:
# Modelo original
my_model$aic
# Modelo con las 2 variables eliminadas
my_model2$aic
# Modelo con las 4 variables eliminadas
my_model3$aic
| Modelo | AIC |
|---|---|
| Modelo Original | 179.2415 |
| Modelo 2 | 175.6393 |
| Modelo 3 | 172.3880 |
Al comparar el AIC del modelo original y los nuevos modelos variables eliminadas, se puede verificar que en el modelo 3 el AIC es menor que el de los otros modelos. Este AIC significa que el nuevo modelo tiene un mejor ajuste del modelo.
Ahora se procederá a eliminar otras 2 variables que tienen un mayor p-valor para poder obtener un mejor ajuste del modelo.
my_model4=glm(data=records,DEATH_EVENT~.-high_blood_pressure-smoking-platelets-diabetes-creatinine_phosphokinase-serum_sodium ,
family = binomial(link = "logit"))
summary(my_model4)
##
## Call:
## glm(formula = DEATH_EVENT ~ . - high_blood_pressure - smoking -
## platelets - diabetes - creatinine_phosphokinase - serum_sodium,
## family = binomial(link = "logit"), data = records)
##
## Coefficients:
## Estimate Std. Error z value Pr(>|z|)
## (Intercept) 0.708705 1.385597 0.511 0.60902
## age 0.053327 0.017994 2.964 0.00304 **
## anaemia 0.401068 0.403233 0.995 0.31992
## ejection_fraction -0.073797 0.018512 -3.986 6.71e-05 ***
## serum_creatinine 0.569549 0.176790 3.222 0.00127 **
## sex -1.077485 0.441182 -2.442 0.01460 *
## time -0.021078 0.003659 -5.761 8.37e-09 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## (Dispersion parameter for binomial family taken to be 1)
##
## Null deviance: 259.12 on 208 degrees of freedom
## Residual deviance: 158.21 on 202 degrees of freedom
## AIC: 172.21
##
## Number of Fisher Scoring iterations: 5
En el resultado anterior, se puede observar que las variables significativas son:
# Modelo original
my_model$aic
# Modelo con las 2 variables eliminadas
my_model2$aic
# Modelo con las 4 variables eliminadas
my_model3$aic
# Modelo con las 6 variables eliminadas
my_model4$aic
| Modelo | AIC |
|---|---|
| Modelo Original | 179.2415 |
| Modelo 2 | 175.6393 |
| Modelo 3 | 172.3880 |
| Modelo 4 | 172.2077 |
Al comparar el AIC del modelo original y los nuevos modelos variables eliminadas, se puede verificar que en el modelo 4 el AIC es menor que el de los otros modelos. Este AIC significa que el nuevo modelo tiene un mejor ajuste del modelo. Aunque comparado con el AIC de modelo 3, la diferencia solo es de -0.1803.
Ahora se procederá a eliminar otras 2 variables que tienen un mayor p-valor para poder obtener un mejor ajuste del modelo.
my_model5=glm(data=records,DEATH_EVENT~.-high_blood_pressure-smoking-platelets-diabetes-creatinine_phosphokinase-serum_sodium-anaemia-sex-1 ,family = binomial(link = "logit"))
summary(my_model5)
##
## Call:
## glm(formula = DEATH_EVENT ~ . - high_blood_pressure - smoking -
## platelets - diabetes - creatinine_phosphokinase - serum_sodium -
## anaemia - sex - 1, family = binomial(link = "logit"), data = records)
##
## Coefficients:
## Estimate Std. Error z value Pr(>|z|)
## age 0.047627 0.010969 4.342 1.41e-05 ***
## ejection_fraction -0.062928 0.015835 -3.974 7.07e-05 ***
## serum_creatinine 0.612431 0.178637 3.428 0.000607 ***
## time -0.020307 0.003297 -6.159 7.31e-10 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## (Dispersion parameter for binomial family taken to be 1)
##
## Null deviance: 289.74 on 209 degrees of freedom
## Residual deviance: 165.67 on 205 degrees of freedom
## AIC: 173.67
##
## Number of Fisher Scoring iterations: 5
Este modelo (my_model5) ha reducido significativamente el número de predictores a aquellos que son altamente significativos, proporcionando un mejor enfoque. Las variables:
permanecen como predictores significativos de la probabilidad de muerte. Es decir, todas estas variables son significativas para el modelo. Esto mejora la interpretabilidad del modelo y potencialmente su estabilidad predictiva.
# Modelo original
my_model$aic
# Modelo con las 2 variables eliminadas
my_model2$aic
# Modelo con las 4 variables eliminadas
my_model3$aic
# Modelo con las 6 variables eliminadas
my_model4$aic
# Modelo con las 8 variables eliminadas
my_model5$aic
| Modelo | AIC |
|---|---|
| Modelo Original | 179.2415 |
| Modelo 2 | 175.6393 |
| Modelo 3 | 172.3880 |
| Modelo 4 | 172.2077 |
| Modelo 5 | 173.6705 |
Al comparar el AIC del modelo original y los nuevos modelos variables eliminadas, se puede verificar que en el modelo 4 el AIC es menor que el de los otros modelos. Sin embargo, en el modelo 4 aun se encuentran variables no significativas, mientras que en el modelo 5 todas las variables son significativas, lo que implica que todas las variables del modelo contribuyen de manera importante a la predicción del evento de interés. Por lo que se trabajará con este ultimo modelo, es decir, el modelo 5.
age: El signo del coeficiente sugiere que a medida que aumenta la edad, la probabilidad de muerte también aumenta.
ejection_fraction: El signo del coeficiente sugiere que una mejor función cardíaca (mayor fracción de eyección) reduce la probabilidad de muerte.
serum_creatinine: El signo del coeficiente sugiere que niveles más altos de creatinina en suero (indicativo de problemas renales) aumentan la probabilidad de muerte.
time: El signo del coeficiente sugiere que un tiempo de seguimiento más largo se asocia con una menor probabilidad de muerte, esto podría significar que los pacientes que sobreviven más tiempo tienen un mejor pronóstico.
La prueba de Wald se utiliza para comparar modelos anidados, es decir, un modelo completo y un modelo reducido, para verificar si la simplificación es justificable. Esta prueba evalúa si la restricción de ciertas variables (es decir, si sus coeficientes son 0) en el modelo reducido es razonable o si esas variables son necesarias para explicar la variabilidad en la variable dependiente.
library(zoo)
library(lmtest)
waldtest(my_model,my_model5)
## Wald test
##
## Model 1: DEATH_EVENT ~ age + anaemia + creatinine_phosphokinase + diabetes +
## ejection_fraction + high_blood_pressure + platelets + serum_creatinine +
## serum_sodium + sex + smoking + time
## Model 2: DEATH_EVENT ~ (age + anaemia + creatinine_phosphokinase + diabetes +
## ejection_fraction + high_blood_pressure + platelets + serum_creatinine +
## serum_sodium + sex + smoking + time) - high_blood_pressure -
## smoking - platelets - diabetes - creatinine_phosphokinase -
## serum_sodium - anaemia - sex - 1
## Res.Df Df F Pr(>F)
## 1 196
## 2 205 -9 1.1655 0.3191
En el resultado anterior se puede observar que el \(p-valor = 0.3191\) indica que no hay suficiente evidencia estadística para rechazar la hipótesis nula de que las variables eliminadas del modelo no contribuyen significativamente a explicar la variabilidad de DEATH_EVENT. Es decir, esto significa que el modelo reducido (my_model5) no es significativamente peor que el modelo completo (my_model). Por lo tanto, es razonable utilizar el modelo reducido, ya que es menos complejo y parece retener las variables más informativas y significativas.
Las pruebas de bondad de ajuste son medidas que evalúan la capacidad del modelo para explicar la variabilidad en los datos y si el modelo es una representación adecuada de la relación entre las variables dependientes e independientes.
La librería ResourceSelection proporciona herramientas para evaluar la bondad de ajuste de los modelos de regresión logística, incluyendo la prueba de Hosmer-Lemeshow.
Esta prueba evalúa la bondad de ajuste de un modelo de regresión logística. Compara los valores observados con los valores predichos por el modelo, agrupando los datos en deciles de riesgo.
library(ResourceSelection)
hoslem.test(records$DEATH_EVENT,fitted(my_model5))
##
## Hosmer and Lemeshow goodness of fit (GOF) test
##
## data: records$DEATH_EVENT, fitted(my_model5)
## X-squared = 8.2596, df = 8, p-value = 0.4085
La prueba de Hosmer-Lemeshow se utiliza para evaluar si hay una discrepancia significativa entre los valores observados y los predichos por el modelo. Un p-valor alto (generalmente mayor a 0.05) indica que no hay suficiente evidencia para rechazar la hipótesis nula de que el modelo tiene un buen ajuste. En este caso, con un p-valor de 0.4085, no hay indicios de un mal ajuste, lo que sugiere que el modelo my_model5 se ajusta adecuadamente a los datos.
Dado que ya se verifico la significancia de las variables y se comprobo el ajuste del modelo, se puede proceder a la extracción de los coeficientes formales del modelo. Estos coeficientes ayudan a entender cómo cada variable afecta la probabilidad de ocurrencia del evento de interés (muerte del paciente en este caso). La dirección y magnitud de los coeficientes indican el tipo y la fuerza de la relación entre cada predictor y la variable de respuesta.
coef(my_model5)
| Coeficientes | |
|---|---|
| age | 0.0476267 |
| ejection_fraction | -0.0629279 |
| serum_creatinine | 0.6124310 |
| time | -0.0203075 |
age (0.0476): Un incremento de un año en la edad se asocia con un aumento del 4.76% en el logaritmo de las probabilidades de DEATH_EVENT.
ejection_fraction (-0.0629): Por cada punto porcentual de incremento en la fracción de eyección, el logaritmo de las probabilidades de DEATH_EVENT disminuye en 6.29%.
serum_creatinine (0.6124): Un incremento de una unidad en los niveles de creatinina en suero se asocia con un aumento del 61.24% en el logaritmo de las probabilidades de DEATH_EVENT.
time (-0.0203): Por cada día adicional, el logaritmo de las probabilidades de DEATH_EVENT disminuye en 2.03%.
Otra forma de obtener estos coeficientes es por medio del siguiente código:
my_model5$coefficients
| Coeficientes | |
|---|---|
| age | 0.0476267 |
| ejection_fraction | -0.0629279 |
| serum_creatinine | 0.6124310 |
| time | -0.0203075 |
Se puede observar que es el mismo resultado que con el código anterior.
Para poder conocer la variabilidad estimada en estos coeficientes se deben obtener los intervalos de confianza para cada variable:
confint(my_model5)
| 2.5 % | 97.5 % | |
|---|---|---|
| age | 0.0271278 | 0.0705157 |
| ejection_fraction | -0.0957236 | -0.0333428 |
| serum_creatinine | 0.2675514 | 0.9885516 |
| time | -0.0273168 | -0.0143120 |
Como los intervalos anteriores no contienen el valor cero, esto indica que las variables tiene un efecto estadísticamente significativo en el modelo. Además, de acuerdo con los resultados se puede decir que el valor de los coeficientes esta dentro de los intervalos obtenidos, con un 95% de confianza.
Las predicciones son los valores estimados para la variable dependiente o de respuesta basados en los valores de las variables independientes o predictoras.
Las predicciones que se utilizarán se obtendrán en la escala de probabilidad, es decir, las probabilidades predichas de que ocurra el evento (muerte) para cada observación en los datos.
y=predict(my_model5,type='response')
y
## 166 231 70 192 251 102
## 0.395337332 0.100403958 0.782907081 0.034144461 0.028029152 0.424621188
## 110 103 23 146 123 188
## 0.259192557 0.758388640 0.765159807 0.205505369 0.268245654 0.284474942
## 125 26 164 101 159 240
## 0.658578649 0.892393393 0.138394211 0.605745862 0.318827534 0.022433962
## 68 133 73 191 274 171
## 0.759213560 0.144733928 0.730288932 0.345307371 0.006284166 0.141918277
## 242 297 198 278 79 162
## 0.091030220 0.001125953 0.111120945 0.032947115 0.511360771 0.116445356
## 150 114 88 17 230 148
## 0.244337847 0.186439489 0.142548706 0.882792890 0.166200267 0.082422799
## 67 130 169 121 201 155
## 0.630084525 0.567515754 0.160839958 0.126902100 0.039934661 0.258517279
## 293 126 207 210 279 19
## 0.010544370 0.093459443 0.019462792 0.040066777 0.016734066 0.887802844
## 16 236 226 284 127 106
## 0.784343438 0.045229512 0.029048934 0.024157346 0.593008011 0.688981827
## 44 22 38 120 27 245
## 0.556017419 0.855899307 0.681832007 0.710163515 0.894019698 0.045541110
## 13 33 174 149 115 89
## 0.669440978 0.555441613 0.205516540 0.624847107 0.315922634 0.168383525
## 95 173 75 137 291 214
## 0.291992370 0.061052966 0.782476760 0.090986708 0.002359596 0.073019672
## 285 94 46 176 7 29
## 0.008812797 0.659333870 0.608957966 0.036596226 0.959298131 0.967554059
## 129 147 109 113 227 256
## 0.339419859 0.221494096 0.376563903 0.490090614 0.101769551 0.039725469
## 259 235 218 253 138 275
## 0.026319711 0.020270242 0.425192989 0.014714604 0.680988745 0.032510885
## 65 289 37 276 157 80
## 0.030836646 0.025786636 0.758269882 0.008719470 0.213261305 0.237968571
## 197 187 220 76 58 205
## 0.036184536 0.020026246 0.040899673 0.633045075 0.404040780 0.102382882
## 223 64 172 57 139 263
## 0.026332184 0.335013147 0.079130007 0.844007734 0.303561812 0.083761035
## 225 20 151 45 1 143
## 0.086160350 0.421664523 0.448455981 0.286071315 0.967574113 0.237067347
## 117 258 219 209 228 132
## 0.083304779 0.024430386 0.091891616 0.054962390 0.040937434 0.830444338
## 239 249 85 272 39 128
## 0.044213115 0.017450683 0.565921143 0.011074388 0.854349946 0.066897466
## 141 165 112 193 158 136
## 0.469796577 0.155694064 0.337208199 0.036937801 0.265743863 0.402432254
## 215 71 202 267 262 53
## 0.071994962 0.189174633 0.008185057 0.082229261 0.020488416 0.904424693
## 177 43 287 77 118 69
## 0.167473913 0.638044435 0.032907162 0.189293127 0.580171199 0.760477293
## 48 232 222 156 252 260
## 0.505375720 0.081744096 0.031114435 0.472189689 0.030496720 0.007506146
## 216 244 14 108 264 189
## 0.131299292 0.056536818 0.608346786 0.214983764 0.008684507 0.075285552
## 154 93 175 277 281 269
## 0.180190295 0.061925716 0.179396727 0.040300421 0.026942039 0.009453343
## 255 41 83 49 211 84
## 0.006658840 0.928676190 0.777612889 0.988034265 0.280642932 0.533577040
## 134 24 160 163 56 145
## 0.104151261 0.230006195 0.141206330 0.187969008 0.945121432 0.655415823
## 208 63 105 74 243 229
## 0.169483091 0.468098441 0.343677511 0.328134597 0.019285768 0.594126598
## 282 11 32 182 196 107
## 0.068718354 0.968549768 0.923097769 0.232025677 0.152198121 0.230909790
## 194 237 206 72 119 8
## 0.206892447 0.041289750 0.025693645 0.418053795 0.115306305 0.389962353
## 204 296 180 9 28 50
## 0.408642548 0.010558667 0.079136308 0.430698001 0.683581841 0.642539655
## 299 31 233 82 292 153
## 0.005177953 0.934508416 0.018155176 0.315160545 0.023504159 0.091495439
## 221 15 81 92 111
## 0.335829566 0.693091861 0.582933699 0.271640102 0.305730548
Ahora se debe convertir la variable y en una variable binaria a la que se llamará pred, donde los valores mayores a 0.5 se convertirán en 1 y los valores iguales o menores a 0.5 se convertirán en 0. Este umbral de 0.5 se utiliza para clasificar las probabilidades en predicciones finales de 0 o 1.
pred=ifelse(as.double(y)>0.5,1,0)
pred
## [1] 0 0 1 0 0 0 0 1 1 0 0 0 1 1 0 1 0 0 1 0 1 0 0 0 0 0 0 0 1 0 0 0 0 1 0 0 1
## [38] 1 0 0 0 0 0 0 0 0 0 1 1 0 0 0 1 1 1 1 1 1 1 0 1 1 0 1 0 0 0 0 1 0 0 0 0 1
## [75] 1 0 1 1 0 0 0 0 0 0 0 0 0 0 1 0 0 0 1 0 0 0 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0
## [112] 0 1 0 0 0 0 0 0 1 0 0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 1 0 1 0 0 1 1 1 0 0 0
## [149] 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 1 1 1 0 1 0 0 0 0 1 1 0 0 0 0 0 1 0 1 1 0 0
## [186] 0 0 0 0 0 0 0 0 0 0 0 1 1 0 1 0 0 0 0 0 1 1 0 0
La salida anterior muestra las clasificaciones finales para cada observación, donde 1 indica que el modelo predice que DEATH_EVENT es 1 (muerte) y 0 indica que predice que DEATH_EVENT es 0 (no muerte). Para poder realizar una mejor comparación entre las probabilidades y las clasificaciones binarias se usará la siguiente tabla:
data.frame(y=y,pred=pred)
| y | pred | |
|---|---|---|
| 166 | 0.3953373 | 0 |
| 231 | 0.1004040 | 0 |
| 70 | 0.7829071 | 1 |
| 192 | 0.0341445 | 0 |
| 251 | 0.0280292 | 0 |
| 102 | 0.4246212 | 0 |
| 110 | 0.2591926 | 0 |
| 103 | 0.7583886 | 1 |
| 23 | 0.7651598 | 1 |
| 146 | 0.2055054 | 0 |
| 123 | 0.2682457 | 0 |
| 188 | 0.2844749 | 0 |
| 125 | 0.6585786 | 1 |
| 26 | 0.8923934 | 1 |
| 164 | 0.1383942 | 0 |
| 101 | 0.6057459 | 1 |
| 159 | 0.3188275 | 0 |
| 240 | 0.0224340 | 0 |
| 68 | 0.7592136 | 1 |
| 133 | 0.1447339 | 0 |
| 73 | 0.7302889 | 1 |
| 191 | 0.3453074 | 0 |
| 274 | 0.0062842 | 0 |
| 171 | 0.1419183 | 0 |
| 242 | 0.0910302 | 0 |
| 297 | 0.0011260 | 0 |
| 198 | 0.1111209 | 0 |
| 278 | 0.0329471 | 0 |
| 79 | 0.5113608 | 1 |
| 162 | 0.1164454 | 0 |
| 150 | 0.2443378 | 0 |
| 114 | 0.1864395 | 0 |
| 88 | 0.1425487 | 0 |
| 17 | 0.8827929 | 1 |
| 230 | 0.1662003 | 0 |
| 148 | 0.0824228 | 0 |
| 67 | 0.6300845 | 1 |
| 130 | 0.5675158 | 1 |
| 169 | 0.1608400 | 0 |
| 121 | 0.1269021 | 0 |
| 201 | 0.0399347 | 0 |
| 155 | 0.2585173 | 0 |
| 293 | 0.0105444 | 0 |
| 126 | 0.0934594 | 0 |
| 207 | 0.0194628 | 0 |
| 210 | 0.0400668 | 0 |
| 279 | 0.0167341 | 0 |
| 19 | 0.8878028 | 1 |
| 16 | 0.7843434 | 1 |
| 236 | 0.0452295 | 0 |
| 226 | 0.0290489 | 0 |
| 284 | 0.0241573 | 0 |
| 127 | 0.5930080 | 1 |
| 106 | 0.6889818 | 1 |
| 44 | 0.5560174 | 1 |
| 22 | 0.8558993 | 1 |
| 38 | 0.6818320 | 1 |
| 120 | 0.7101635 | 1 |
| 27 | 0.8940197 | 1 |
| 245 | 0.0455411 | 0 |
| 13 | 0.6694410 | 1 |
| 33 | 0.5554416 | 1 |
| 174 | 0.2055165 | 0 |
| 149 | 0.6248471 | 1 |
| 115 | 0.3159226 | 0 |
| 89 | 0.1683835 | 0 |
| 95 | 0.2919924 | 0 |
| 173 | 0.0610530 | 0 |
| 75 | 0.7824768 | 1 |
| 137 | 0.0909867 | 0 |
| 291 | 0.0023596 | 0 |
| 214 | 0.0730197 | 0 |
| 285 | 0.0088128 | 0 |
| 94 | 0.6593339 | 1 |
| 46 | 0.6089580 | 1 |
| 176 | 0.0365962 | 0 |
| 7 | 0.9592981 | 1 |
| 29 | 0.9675541 | 1 |
| 129 | 0.3394199 | 0 |
| 147 | 0.2214941 | 0 |
| 109 | 0.3765639 | 0 |
| 113 | 0.4900906 | 0 |
| 227 | 0.1017696 | 0 |
| 256 | 0.0397255 | 0 |
| 259 | 0.0263197 | 0 |
| 235 | 0.0202702 | 0 |
| 218 | 0.4251930 | 0 |
| 253 | 0.0147146 | 0 |
| 138 | 0.6809887 | 1 |
| 275 | 0.0325109 | 0 |
| 65 | 0.0308366 | 0 |
| 289 | 0.0257866 | 0 |
| 37 | 0.7582699 | 1 |
| 276 | 0.0087195 | 0 |
| 157 | 0.2132613 | 0 |
| 80 | 0.2379686 | 0 |
| 197 | 0.0361845 | 0 |
| 187 | 0.0200262 | 0 |
| 220 | 0.0408997 | 0 |
| 76 | 0.6330451 | 1 |
| 58 | 0.4040408 | 0 |
| 205 | 0.1023829 | 0 |
| 223 | 0.0263322 | 0 |
| 64 | 0.3350131 | 0 |
| 172 | 0.0791300 | 0 |
| 57 | 0.8440077 | 1 |
| 139 | 0.3035618 | 0 |
| 263 | 0.0837610 | 0 |
| 225 | 0.0861604 | 0 |
| 20 | 0.4216645 | 0 |
| 151 | 0.4484560 | 0 |
| 45 | 0.2860713 | 0 |
| 1 | 0.9675741 | 1 |
| 143 | 0.2370673 | 0 |
| 117 | 0.0833048 | 0 |
| 258 | 0.0244304 | 0 |
| 219 | 0.0918916 | 0 |
| 209 | 0.0549624 | 0 |
| 228 | 0.0409374 | 0 |
| 132 | 0.8304443 | 1 |
| 239 | 0.0442131 | 0 |
| 249 | 0.0174507 | 0 |
| 85 | 0.5659211 | 1 |
| 272 | 0.0110744 | 0 |
| 39 | 0.8543499 | 1 |
| 128 | 0.0668975 | 0 |
| 141 | 0.4697966 | 0 |
| 165 | 0.1556941 | 0 |
| 112 | 0.3372082 | 0 |
| 193 | 0.0369378 | 0 |
| 158 | 0.2657439 | 0 |
| 136 | 0.4024323 | 0 |
| 215 | 0.0719950 | 0 |
| 71 | 0.1891746 | 0 |
| 202 | 0.0081851 | 0 |
| 267 | 0.0822293 | 0 |
| 262 | 0.0204884 | 0 |
| 53 | 0.9044247 | 1 |
| 177 | 0.1674739 | 0 |
| 43 | 0.6380444 | 1 |
| 287 | 0.0329072 | 0 |
| 77 | 0.1892931 | 0 |
| 118 | 0.5801712 | 1 |
| 69 | 0.7604773 | 1 |
| 48 | 0.5053757 | 1 |
| 232 | 0.0817441 | 0 |
| 222 | 0.0311144 | 0 |
| 156 | 0.4721897 | 0 |
| 252 | 0.0304967 | 0 |
| 260 | 0.0075061 | 0 |
| 216 | 0.1312993 | 0 |
| 244 | 0.0565368 | 0 |
| 14 | 0.6083468 | 1 |
| 108 | 0.2149838 | 0 |
| 264 | 0.0086845 | 0 |
| 189 | 0.0752856 | 0 |
| 154 | 0.1801903 | 0 |
| 93 | 0.0619257 | 0 |
| 175 | 0.1793967 | 0 |
| 277 | 0.0403004 | 0 |
| 281 | 0.0269420 | 0 |
| 269 | 0.0094533 | 0 |
| 255 | 0.0066588 | 0 |
| 41 | 0.9286762 | 1 |
| 83 | 0.7776129 | 1 |
| 49 | 0.9880343 | 1 |
| 211 | 0.2806429 | 0 |
| 84 | 0.5335770 | 1 |
| 134 | 0.1041513 | 0 |
| 24 | 0.2300062 | 0 |
| 160 | 0.1412063 | 0 |
| 163 | 0.1879690 | 0 |
| 56 | 0.9451214 | 1 |
| 145 | 0.6554158 | 1 |
| 208 | 0.1694831 | 0 |
| 63 | 0.4680984 | 0 |
| 105 | 0.3436775 | 0 |
| 74 | 0.3281346 | 0 |
| 243 | 0.0192858 | 0 |
| 229 | 0.5941266 | 1 |
| 282 | 0.0687184 | 0 |
| 11 | 0.9685498 | 1 |
| 32 | 0.9230978 | 1 |
| 182 | 0.2320257 | 0 |
| 196 | 0.1521981 | 0 |
| 107 | 0.2309098 | 0 |
| 194 | 0.2068924 | 0 |
| 237 | 0.0412897 | 0 |
| 206 | 0.0256936 | 0 |
| 72 | 0.4180538 | 0 |
| 119 | 0.1153063 | 0 |
| 8 | 0.3899624 | 0 |
| 204 | 0.4086425 | 0 |
| 296 | 0.0105587 | 0 |
| 180 | 0.0791363 | 0 |
| 9 | 0.4306980 | 0 |
| 28 | 0.6835818 | 1 |
| 50 | 0.6425397 | 1 |
| 299 | 0.0051780 | 0 |
| 31 | 0.9345084 | 1 |
| 233 | 0.0181552 | 0 |
| 82 | 0.3151605 | 0 |
| 292 | 0.0235042 | 0 |
| 153 | 0.0914954 | 0 |
| 221 | 0.3358296 | 0 |
| 15 | 0.6930919 | 1 |
| 81 | 0.5829337 | 1 |
| 92 | 0.2716401 | 0 |
| 111 | 0.3057305 | 0 |
La prueba se realizará con los siguientes datos:
nd=data.frame(age=50.0,ejection_fraction=35.0,serum_creatinine=0.75,time=6)
nd
| age | ejection_fraction | serum_creatinine | time |
|---|---|---|---|
| 50 | 35 | 0.75 | 6 |
Para garantizar que la prueba que se llevará acabo sea de forma correcta, se deben excluir del modelo las variables no significativas de la siguiente forma:
# Eliminar variables no deseadas del data frame original
var_para_predicciones <- records[, !(names(records) %in% c("anaemia", "high_blood_pressure", "smoking", "platelets", "diabetes", "creatinine_phosphokinase", "serum_sodium", "sex"))]
# Ajustar el modelo sin las variables eliminadas
my_model_final <- glm(data = var_para_predicciones, DEATH_EVENT ~ .-1, family = binomial(link = "logit"))
summary(my_model_final)
##
## Call:
## glm(formula = DEATH_EVENT ~ . - 1, family = binomial(link = "logit"),
## data = var_para_predicciones)
##
## Coefficients:
## Estimate Std. Error z value Pr(>|z|)
## age 0.047627 0.010969 4.342 1.41e-05 ***
## ejection_fraction -0.062928 0.015835 -3.974 7.07e-05 ***
## serum_creatinine 0.612431 0.178637 3.428 0.000607 ***
## time -0.020307 0.003297 -6.159 7.31e-10 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## (Dispersion parameter for binomial family taken to be 1)
##
## Null deviance: 289.74 on 209 degrees of freedom
## Residual deviance: 165.67 on 205 degrees of freedom
## AIC: 173.67
##
## Number of Fisher Scoring iterations: 5
Se puede observar que el modelo es el mismo que el my_model5, por lo que no se esta alterando nada. Ahora se puede proceder a realizar la predición:
predict(my_model_final, newdata = nd)
## 1
## 0.5163384
La predicción obtenida indica que, según el modelo, el individuo con las características especificadas en nd tiene una probabilidad del 51.6% de experimentar el evento DEATH_EVENT (muerte del paciente). Este resultado puede ser utilizado en el contexto de análisis de riesgo o para informar decisiones médicas, siempre considerando la precisión y las limitaciones del modelo.
Ahora se va evalúar la precisión de un modelo de regresión logística utilizando dos conjuntos de predicciones y luego se comparan estas precisiones con el valor real del evento de muerte (DEATH_EVENT).
library(MLmetrics)
Accuracy(pred,records$DEATH_EVENT)
## [1] 0.8277512
La precisión calculada para pred es 0.8277512, lo que significa que el modelo clasificó correctamente el 82.8% de los casos.
Se asignará a pred2 las clasificaciones según las probabilidades de las predicciones:
pred2=ifelse(my_model$fitted.values>0.5,1,0)
pred2
## 166 231 70 192 251 102 110 103 23 146 123 188 125 26 164 101 159 240 68 133
## 1 0 1 0 0 0 0 1 1 0 0 0 1 1 1 0 0 0 1 0
## 73 191 274 171 242 297 198 278 79 162 150 114 88 17 230 148 67 130 169 121
## 1 0 0 0 0 0 0 0 1 0 0 0 0 1 0 0 1 0 0 0
## 201 155 293 126 207 210 279 19 16 236 226 284 127 106 44 22 38 120 27 245
## 0 0 0 0 0 0 0 1 1 0 0 0 1 1 0 1 1 1 1 0
## 13 33 174 149 115 89 95 173 75 137 291 214 285 94 46 176 7 29 129 147
## 1 1 0 1 0 0 0 0 1 0 0 0 0 1 1 0 1 1 0 0
## 109 113 227 256 259 235 218 253 138 275 65 289 37 276 157 80 197 187 220 76
## 0 0 0 0 0 0 0 0 1 0 0 0 1 0 0 0 0 0 0 1
## 58 205 223 64 172 57 139 263 225 20 151 45 1 143 117 258 219 209 228 132
## 0 0 0 0 0 1 0 0 0 1 1 0 1 0 0 0 0 0 0 1
## 239 249 85 272 39 128 141 165 112 193 158 136 215 71 202 267 262 53 177 43
## 0 0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 1 0 1
## 287 77 118 69 48 232 222 156 252 260 216 244 14 108 264 189 154 93 175 277
## 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
## 281 269 255 41 83 49 211 84 134 24 160 163 56 145 208 63 105 74 243 229
## 0 0 0 1 1 1 0 0 0 0 0 0 1 1 0 0 0 0 0 1
## 282 11 32 182 196 107 194 237 206 72 119 8 204 296 180 9 28 50 299 31
## 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 0 1
## 233 82 292 153 221 15 81 92 111
## 0 0 0 0 0 1 1 0 0
Volviendo a evaluar la precisión del modelo:
Accuracy(pred2,records$DEATH_EVENT)
## [1] 0.8564593
La precisión para pred2 es 0.8564593, lo que indica que el modelo clasificó correctamente el 85.6% de los casos con este nuevo conjunto de predicciones.
El aumento en precisión al cambiar de pred a pred2 sugiere una mejora en la capacidad del modelo para hacer predicciones correctas.