library(readr)
library(ggplot2)
library(reshape2)
library(GGally)
library(dplyr)
##
## Attaching package: 'dplyr'
## The following objects are masked from 'package:stats':
##
## filter, lag
## The following objects are masked from 'package:base':
##
## intersect, setdiff, setequal, union
library(car)
## Loading required package: carData
##
## Attaching package: 'car'
## The following object is masked from 'package:dplyr':
##
## recode
library(patchwork)
library(broom)
En este trabajo se estudia la relación entre la resistencia a la compresión del concreto y la composición de la mezcla, así como la edad de curado. La base de datos contiene distintas mezclas de concreto con sus proporciones (en kg por m³) y la resistencia medida (en MPa).
El objetivo general es construir y analizar un modelo de regresión lineal múltiple que permita explicar y predecir la resistencia a la compresión (csMPa) a partir de los componentes del concreto y su edad (age).
A continuación se resumen las variables utilizadas en el análisis.
Estas son las variables cuantitativas predictoras (covariables) utilizadas en el modelo.
| Descriptive Name | DataFrame Name | Unit / Description |
|---|---|---|
| Cement (component 1) | cement | kg in a 1 m³ mixture |
| Blast Furnace Slag (component 2) | slag | kg in a 1 m³ mixture |
| Fly Ash (component 3) | flyash | kg in a 1 m³ mixture |
| Water (component 4) | water | kg in a 1 m³ mixture |
| Superplasticizer (component 5) | superplasticizer | kg in a 1 m³ mixture |
| Coarse Aggregate (component 6) | coarseaggregate | kg in a 1 m³ mixture |
| Fine Aggregate (component 7) | fineaggregate | kg in a 1 m³ mixture |
| Age | age | Days (1–365) |
Estas covariables resumen la composición física de la mezcla y el tiempo de curado, ambos factores clave para la resistencia final del concreto.
Esta es la variable cuantitativa de respuesta que se desea explicar y predecir.
| Descriptive Name | DataFrame Name | Unit / Description |
|---|---|---|
| Concrete compressive strength | csMPa | MPa (Megapascals) |
csMPa representa la resistencia a la compresión del
concreto medida en megapascales, que es el principal indicador de
calidad estructural de la mezcla.
El interés principal es evaluar si los componentes del concreto y su tiempo de curado (edad) tienen una relación estadísticamente significativa con la resistencia a la compresión.
A nivel formal, consideramos el modelo lineal múltiple:
\[ csMPa_{i} = \beta_{0} + \beta_{1} \text{cement}_{i} + \beta_{2} \text{slag}_{i} + \cdots + \beta_{p} X_{pi} + \epsilon_{i} \]
donde \(\epsilon_{i} \sim N(0, \sigma^2)\) independientes.
Hipótesis global del modelo:
\[ H_{0}: \beta_{1} = \beta_{2} = \cdots = \beta_{p} = 0 \text{ (las covariables no explican la resistencia)} \] \[ H_{1}: \exists j \text{ tal que } \beta_{j} \neq 0 \text{ (al menos una covariable tiene efecto)} \]
Hipótesis individuales (por covariable \(X_{j}\)):
\[ H_{0}: \beta_{j} = 0 \text{ (no hay asociación lineal con csMPa)} \] \[ H_{1}: \beta_{j} \neq 0 \text{ (sí hay asociación lineal con csMPa)} \]
En particular, nos interesa comprobar si:
log_age) mejora
la explicación de la resistencia. ## 1.3 Carga de datos y transformación
inicialdf = read_csv("/Users/usermac/Documents/especializacion/metodos de regresion/trabajo2/Concrete_Data_Yeh.csv")
## Rows: 1030 Columns: 9
## ── Column specification ────────────────────────────────────────────────────────
## Delimiter: ","
## dbl (9): cement, slag, flyash, water, superplasticizer, coarseaggregate, fin...
##
## ℹ Use `spec()` to retrieve the full column specification for this data.
## ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
Se crea además la transformación logarítmica de la edad y de la resistencia, ya que es común que la relación con la edad sea aproximadamente logarítmica y que la respuesta presente asimetría:
df$log_age = log(df$age)
df$log_csmpa = log(df$csMPa)
Primero, se explora la distribución de la resistencia y de algunos componentes
ggplot(df, aes(x = csMPa)) +
geom_density() +
labs(title = "Gráfico de Densidad csMPa",
x = "csMPa",
y = "Densidad")
Este gráfico permite visualizar si csMPa es aproximadamente simétrica o presenta sesgo (por ejemplo, hacia la derecha), lo que justifica el uso del logaritmo.
ggplot(df, aes(x = cement)) +
geom_density() +
labs(title = "Gráfico de Densidad cement",
x = "cement",
y = "Densidad")
De forma similar, se puede observar la distribución de cement,
identificando rangos típicos de contenido de cemento en la mezcla.
Para tener una idea general del tamaño de la base, de los rangos de valores y de posibles valores perdidos (NA), se imprimen los datos y se revisan los NA:
En esta sección se estudian las relaciones bivariadas entre csMPa (y su logaritmo) y las diferentes covariables. Esto permite detectar patrones de linealidad, posibles outliers y motivar transformaciones.
p1 <- ggplot(data=df, aes(x=cement, y = csMPa)) +
geom_point(alpha = 0.7, size=2, colour = "darkgreen") +
labs(
title = "Cement vs csMPa",
x = "cement (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p2 <- ggplot(data=df, aes(x=cement, y = log(csMPa))) +
geom_point(alpha = 0.7, size=2, colour = "darkblue") +
labs(
title = "Cement vs log(csMPa)",
x = "cement (kg/m^3)",
y = "log(cMPa)"
) +
theme_minimal()
p1 + p2
En general se espera una relación positiva: a mayor contenido de
cemento, mayor resistencia. El gráfico con log(csMPa) ayuda a ver si la
relación se vuelve más cercana a lineal.
p1 <- ggplot(data=df, aes(x=slag, y = csMPa)) +
geom_point(alpha = 0.7, size=2, colour = "darkgreen") +
labs(
title = "slag vs csMPa",
x = "slag (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p2 <- ggplot(data=df, aes(x=slag, y = log(csMPa))) +
geom_point(alpha = 0.7, size=2, colour = "darkblue") +
labs(
title = "slag vs log(csMPa)",
x = "slag (kg/m^3)",
y = "log(cMPa)"
) +
theme_minimal()
p1 + p2
La escoria granulada (slag) puede contribuir a la resistencia especialmente en edades mayores. El gráfico permite ver si el efecto es lineal o si hay niveles a partir de los cuales la ganancia de resistencia se estabiliza.
p1 <- ggplot(data=df, aes(x=water, y = csMPa)) +
geom_point(alpha = 0.7, size=2, colour = "darkgreen") +
labs(
title = "water vs csMPa",
x = "water (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p2 <- ggplot(data=df, aes(x=water, y = log(csMPa))) +
geom_point(alpha = 0.7, size=2, colour = "darkblue") +
labs(
title = "water vs log(csMPa)",
x = "water (kg/m^3)",
y = "log(cMPa)"
) +
theme_minimal()
p1 + p2
Típicamente se espera que un mayor contenido de agua reduzca la resistencia (relación negativa), debido a relaciones agua/cemento más altas.
p1 <- ggplot(data=df, aes(x=superplasticizer, y = csMPa))+
geom_point(alpha = 0.7, size=2, colour = "darkgreen")+
labs(
title = "Superplasticizer vs csMPa",
x = "Superplasticizer (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p2 <- ggplot(data=df, aes(x=superplasticizer, y = log_csmpa))+
geom_point(alpha = 0.7, size=2, colour = "darkblue")+
labs(
title = "Superplasticizer vs Log_csMPa",
x = "Superplasticizer (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p1+p2
El superplastificante permite reducir agua manteniendo trabajabilidad, por lo que su efecto puede ser indirectamente positivo sobre la resistencia.
p1 <- ggplot(data=df, aes(x=coarseaggregate, y = csMPa))+
geom_point(alpha = 0.7, size=2, colour = "darkgreen")+
labs(
title = "Coarse Aggregate vs csMPa",
x = "Coarse Aggregate (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p2 <- ggplot(data=df, aes(x=coarseaggregate, y = log_csmpa))+
geom_point(alpha = 0.7, size=2, colour = "darkblue")+
labs(
title = "Coarse Aggregate vs log_csmpa",
x = "Coarse Aggregate (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p1 + p2
p1 <- ggplot(data=df, aes(x=fineaggregate, y = csMPa))+
geom_point(alpha = 0.7, size=2, colour = "darkgreen")+
labs(
title = "Fine Aggregate vs csMPa",
x = "Fine Aggregate (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p2 <- ggplot(data=df, aes(x=fineaggregate, y = log_csmpa))+
geom_point(alpha = 0.7, size=2, colour = "darkblue")+
labs(
title = "Fine Aggregate vs log_csmpa",
x = "Fine Aggregate (kg/m^3)",
y = "cMPa"
) +
theme_minimal()
p1 + p2
Los agregados suelen tener un efecto más sutil sobre la resistencia que el cemento o el agua; estas gráficas ayudan a detectar si hay relación clara o si su efecto es más débil.
p1 <- ggplot(data=df, aes(x=age, y = csMPa))+
geom_point(alpha = 0.7, size=2, colour = "darkgreen")+
labs(
title = "Age vs csMPa",
x = "Age (kg/m^3)",
y = "cMPa"
)
p2 <- ggplot(data=df, aes(x=age, y = log_csmpa))+
geom_point(alpha = 0.7, size=2, colour = "darkblue")+
labs(
title = "Age vs log_csmpa",
x = "Age (kg/m^3)",
y = "log_csmpa"
)
p3 <- ggplot(data=df, aes(x=log_age, y = csMPa))+
geom_point(alpha = 0.7, size=2, colour = "darkred")+
labs(
title = "log_age vs csMPa",
x = "log_age",
y = "cMPa"
)
p4 <- ggplot(data=df, aes(x=log_age, y = log_csmpa))+
geom_point(alpha = 0.7, size=2, colour = "darkorange")+
labs(
title = "log_age vs log_csmpa",
x = "log_age",
y = "log_csmpa"
)
(p1 + p2) / (p3 + p4)
Es común que la resistencia aumente rápidamente al inicio y luego se estabilice, lo que hace que log_age sea una transformación razonable para aproximar una relación más lineal con csMPa o log_csmpa. ## 1.6 Matriz de correlación y asociación entre variables.
cormat = round(cor(df),2)
cormat[upper.tri(cormat)] <- NA
head(cormat)
## cement slag flyash water superplasticizer coarseaggregate
## cement 1.00 NA NA NA NA NA
## slag -0.28 1.00 NA NA NA NA
## flyash -0.40 -0.32 1.00 NA NA NA
## water -0.08 0.11 -0.26 1.00 NA NA
## superplasticizer 0.09 0.04 0.38 -0.66 1.00 NA
## coarseaggregate -0.11 -0.28 -0.01 -0.18 -0.27 1
## fineaggregate age csMPa log_age log_csmpa
## cement NA NA NA NA NA
## slag NA NA NA NA NA
## flyash NA NA NA NA NA
## water NA NA NA NA NA
## superplasticizer NA NA NA NA NA
## coarseaggregate NA NA NA NA NA
melted_cormat = melt(cormat, na.rm = TRUE)
head(melted_cormat)
## Var1 Var2 value
## 1 cement cement 1.00
## 2 slag cement -0.28
## 3 flyash cement -0.40
## 4 water cement -0.08
## 5 superplasticizer cement 0.09
## 6 coarseaggregate cement -0.11
ggplot(data=melted_cormat, aes(x=Var1, y=Var2, fill=value))+
geom_tile(color = "white") +
scale_fill_gradient2(
low="blue", high = "red", mid = "white",
midpoint = 0,
limit = c(-1, 1),
name = "correlación"
) +
theme_minimal() +
theme(
axis.text.x = element_text(angle = 45, vjust=1, hjust=1, size=10),
axis.text.y = element_text(size=10),
axis.title = element_blank()
) +
geom_text(aes(label=value), color="black", size=3) +
coord_fixed()
La matriz de correlación permite identificar:
Correlaciones fuertes entre csMPa y algunas covariables (por ejemplo, cemento y edad).
Correlaciones altas entre covariables, lo que puede indicar multicolinealidad (importante para la interpretación de los coeficientes y el VIF más adelante).
También se exploran relaciones más detalladas con ggpairs:
ggpairs(df, columns = c("log_csmpa", "cement", "water", "log_age", "slag"))
Este gráfico resume dispersión, correlaciones y distribuciones
univariadas de las variables seleccionadas.
cuartiles_log_age = quantile(
df$log_age,
probs = c(0, 0.25, 0.5, 0.75, 1),
na.rm = TRUE
)
mediana_slag = quantile(
df$slag,
probs = c(0, 0.5, 1),
na.rm = TRUE
)
cuartiles_water = quantile(
df$water,
probs = c(0, 0.25, 0.5, 0.75, 1),
na.rm = TRUE
)
df = df %>%
mutate(
categoria_log_edad = cut(
log_age,
breaks = cuartiles_log_age,
labels = c("Q1 (0-25%)", "Q2 (25-50%)", "Q3(50-75%)", "Q4 (75-100)%"),
include.lowest = TRUE
)
)
df = df %>%
mutate(
categoria_slag = cut(
slag,
breaks = mediana_slag,
labels = c("lower_median","upper_median"),
include.lowest = TRUE
)
)
df = df %>%
mutate(
categoria_water = cut(
water,
breaks = cuartiles_water,
labels = c("Q1 (0-25%)", "Q2 (25-50%)", "Q3(50-75%)", "Q4 (75-100)%"),
include.lowest = TRUE
)
)
ggplot(
df,
aes(x = cement, y=csMPa, color = categoria_log_edad)
) +
geom_point(alpha=0.3) +
geom_smooth(method = "lm", se=FALSE) +
labs(
title = "Interacción entre cement y cuartiles de edad",
x = "cemento",
y = "resistencia concreto",
color = "Cuartil edad"
) +
theme_minimal()
## `geom_smooth()` using formula = 'y ~ x'
ggplot(
df,
aes(x = water, y=csMPa, color = categoria_log_edad)
) +
geom_point(alpha=0.3) +
geom_smooth(method = "lm", se=FALSE) +
labs(
title = "Interacción entre water y cuartiles de edad",
x = "water",
y = "resistencia concreto",
color = "Cuartil edad"
) +
theme_minimal()
## `geom_smooth()` using formula = 'y ~ x'
ggplot(
df,
aes(x = cement, y=csMPa, color = categoria_slag)
) +
geom_point(alpha=0.3) +
geom_smooth(method = "lm", se=FALSE) +
labs(
title = "Interacción entre cement y categorías de slag",
x = "cemento",
y = "resistencia concreto",
color = "slag"
) +
theme_minimal()
## `geom_smooth()` using formula = 'y ~ x'
ggplot(
df,
aes(x = cement, y=csMPa, color = categoria_water)
) +
geom_point(alpha=0.3) +
geom_smooth(method = "lm", se=FALSE) +
labs(
title = "Interacción entre cement y cuartiles de water",
x = "cemento",
y = "resistencia concreto",
color = "Cuartil water"
) +
theme_minimal()
## `geom_smooth()` using formula = 'y ~ x'
En esta sección se ajustan distintos modelos de regresión lineal múltiple, explorando tanto efectos principales como términos de interacción. Se usa log_csmpa como respuesta para mejorar la linealidad y la normalidad de los residuos.
mlr1 = lm(formula = log_csmpa ~ cement + slag + flyash + water
+ fineaggregate +log_age
+ cement:log_age + cement:flyash + cement:water
+ water:log_age + water:slag, data=df)
summary(mlr1)
##
## Call:
## lm(formula = log_csmpa ~ cement + slag + flyash + water + fineaggregate +
## log_age + cement:log_age + cement:flyash + cement:water +
## water:log_age + water:slag, data = df)
##
## Residuals:
## Min 1Q Median 3Q Max
## -1.0156 -0.1260 0.0159 0.1452 0.7293
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 2.659e+00 3.073e-01 8.654 < 2e-16 ***
## cement 2.975e-03 6.730e-04 4.421 1.09e-05 ***
## slag 1.770e-03 9.419e-04 1.879 0.06048 .
## flyash 1.524e-03 3.796e-04 4.016 6.36e-05 ***
## water -1.244e-02 1.560e-03 -7.974 4.12e-15 ***
## fineaggregate 1.390e-04 1.426e-04 0.975 0.32985
## log_age 4.704e-01 5.200e-02 9.046 < 2e-16 ***
## cement:log_age -7.176e-04 5.907e-05 -12.148 < 2e-16 ***
## cement:flyash 3.501e-06 1.318e-06 2.656 0.00803 **
## cement:water 1.526e-05 3.780e-06 4.038 5.80e-05 ***
## water:log_age 2.480e-04 2.637e-04 0.940 0.34726
## slag:water 5.522e-06 5.192e-06 1.064 0.28780
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.2334 on 1018 degrees of freedom
## Multiple R-squared: 0.8227, Adjusted R-squared: 0.8208
## F-statistic: 429.4 on 11 and 1018 DF, p-value: < 2.2e-16
El modelo mlr1 incluye:
step(mlr1)
## Start: AIC=-2985.56
## log_csmpa ~ cement + slag + flyash + water + fineaggregate +
## log_age + cement:log_age + cement:flyash + cement:water +
## water:log_age + water:slag
##
## Df Sum of Sq RSS AIC
## - water:log_age 1 0.0482 55.494 -2986.7
## - fineaggregate 1 0.0518 55.498 -2986.6
## - slag:water 1 0.0616 55.508 -2986.4
## <none> 55.446 -2985.6
## - cement:flyash 1 0.3842 55.830 -2980.4
## - cement:water 1 0.8880 56.334 -2971.2
## - cement:log_age 1 8.0372 63.483 -2848.1
##
## Step: AIC=-2986.67
## log_csmpa ~ cement + slag + flyash + water + fineaggregate +
## log_age + cement:log_age + cement:flyash + cement:water +
## slag:water
##
## Df Sum of Sq RSS AIC
## - fineaggregate 1 0.0498 55.544 -2987.7
## - slag:water 1 0.0703 55.565 -2987.4
## <none> 55.494 -2986.7
## - cement:flyash 1 0.3739 55.868 -2981.8
## - cement:water 1 0.9105 56.405 -2971.9
## - cement:log_age 1 8.0283 63.523 -2849.5
##
## Step: AIC=-2987.74
## log_csmpa ~ cement + slag + flyash + water + log_age + cement:log_age +
## cement:flyash + cement:water + slag:water
##
## Df Sum of Sq RSS AIC
## - slag:water 1 0.0485 55.593 -2988.8
## <none> 55.544 -2987.7
## - cement:flyash 1 0.4566 56.001 -2981.3
## - cement:water 1 0.8743 56.418 -2973.7
## - cement:log_age 1 8.0723 63.616 -2850.0
##
## Step: AIC=-2988.84
## log_csmpa ~ cement + slag + flyash + water + log_age + cement:log_age +
## cement:flyash + cement:water
##
## Df Sum of Sq RSS AIC
## <none> 55.593 -2988.8
## - cement:flyash 1 0.496 56.089 -2981.7
## - cement:water 1 0.826 56.419 -2975.7
## - cement:log_age 1 8.099 63.691 -2850.8
## - slag 1 36.842 92.434 -2467.1
##
## Call:
## lm(formula = log_csmpa ~ cement + slag + flyash + water + log_age +
## cement:log_age + cement:flyash + cement:water, data = df)
##
## Coefficients:
## (Intercept) cement slag flyash water
## 2.507e+00 3.246e-03 2.706e-03 1.388e-03 -1.084e-02
## log_age cement:log_age cement:flyash cement:water
## 5.169e-01 -7.199e-04 3.857e-06 1.332e-05
mlr1.optimo = lm(formula = log_csmpa ~ cement + slag + flyash + water + log_age +
cement:log_age + cement:flyash + cement:water, data = df)
summary(mlr1.optimo)
##
## Call:
## lm(formula = log_csmpa ~ cement + slag + flyash + water + log_age +
## cement:log_age + cement:flyash + cement:water, data = df)
##
## Residuals:
## Min 1Q Median 3Q Max
## -1.02151 -0.11550 0.01545 0.14552 0.72645
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 2.507e+00 2.138e-01 11.729 < 2e-16 ***
## cement 3.246e-03 6.362e-04 5.102 4.01e-07 ***
## slag 2.706e-03 1.040e-04 26.012 < 2e-16 ***
## flyash 1.388e-03 3.500e-04 3.966 7.80e-05 ***
## water -1.084e-02 1.124e-03 -9.644 < 2e-16 ***
## log_age 5.169e-01 1.863e-02 27.739 < 2e-16 ***
## cement:log_age -7.199e-04 5.902e-05 -12.196 < 2e-16 ***
## cement:flyash 3.857e-06 1.278e-06 3.019 0.002602 **
## cement:water 1.332e-05 3.418e-06 3.895 0.000104 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.2333 on 1021 degrees of freedom
## Multiple R-squared: 0.8222, Adjusted R-squared: 0.8208
## F-statistic: 590.3 on 8 and 1021 DF, p-value: < 2.2e-16
mlr1.optimo es una versión más parsimoniosa, que conserva interacciones que parecen relevantes para explicar log_csmpa.
Como comparación, también se ajusta un modelo sin interacciones:
mlr2 = lm(formula = log_csmpa ~ cement + slag + flyash + water
+ fineaggregate +log_age, data=df)
summary(mlr2)
##
## Call:
## lm(formula = log_csmpa ~ cement + slag + flyash + water + fineaggregate +
## log_age, data = df)
##
## Residuals:
## Min 1Q Median 3Q Max
## -1.31600 -0.12374 0.02711 0.17203 0.73918
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 2.2527006 0.2102143 10.716 <2e-16 ***
## cement 0.0036216 0.0001151 31.452 <2e-16 ***
## slag 0.0027290 0.0001300 20.998 <2e-16 ***
## flyash 0.0025884 0.0001824 14.189 <2e-16 ***
## water -0.0066219 0.0004922 -13.454 <2e-16 ***
## fineaggregate 0.0001056 0.0001395 0.757 0.449
## log_age 0.3019171 0.0066860 45.156 <2e-16 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.2514 on 1023 degrees of freedom
## Multiple R-squared: 0.7933, Adjusted R-squared: 0.7921
## F-statistic: 654.3 on 6 and 1023 DF, p-value: < 2.2e-16
step(mlr2)
## Start: AIC=-2837.5
## log_csmpa ~ cement + slag + flyash + water + fineaggregate +
## log_age
##
## Df Sum of Sq RSS AIC
## - fineaggregate 1 0.036 64.679 -2838.9
## <none> 64.642 -2837.5
## - water 1 11.438 76.080 -2671.7
## - flyash 1 12.722 77.364 -2654.5
## - slag 1 27.862 92.505 -2470.4
## - cement 1 62.507 127.149 -2142.7
## - log_age 1 128.849 193.491 -1710.2
##
## Step: AIC=-2838.92
## log_csmpa ~ cement + slag + flyash + water + log_age
##
## Df Sum of Sq RSS AIC
## <none> 64.679 -2838.9
## - flyash 1 15.454 80.133 -2620.2
## - water 1 18.967 83.646 -2576.1
## - slag 1 38.201 102.880 -2362.9
## - cement 1 90.005 154.684 -1942.8
## - log_age 1 128.995 193.673 -1711.3
##
## Call:
## lm(formula = log_csmpa ~ cement + slag + flyash + water + log_age,
## data = df)
##
## Coefficients:
## (Intercept) cement slag flyash water log_age
## 2.396986 0.003572 0.002675 0.002524 -0.006844 0.301642
mlr2.optimo = lm(formula = log_csmpa ~ cement + slag + flyash + water + log_age,
data = df)
summary(mlr2.optimo)
##
## Call:
## lm(formula = log_csmpa ~ cement + slag + flyash + water + log_age,
## data = df)
##
## Residuals:
## Min 1Q Median 3Q Max
## -1.31104 -0.12159 0.02827 0.17251 0.73636
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 2.397e+00 8.844e-02 27.10 <2e-16 ***
## cement 3.572e-03 9.463e-05 37.75 <2e-16 ***
## slag 2.675e-03 1.088e-04 24.59 <2e-16 ***
## flyash 2.524e-03 1.614e-04 15.64 <2e-16 ***
## water -6.844e-03 3.950e-04 -17.33 <2e-16 ***
## log_age 3.016e-01 6.675e-03 45.19 <2e-16 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.2513 on 1024 degrees of freedom
## Multiple R-squared: 0.7932, Adjusted R-squared: 0.7922
## F-statistic: 785.4 on 5 and 1024 DF, p-value: < 2.2e-16
Para facilitar la interpretación directa en MPa, se ajusta un modelo final usando csMPa como variable respuesta, conservando la estructura de covariables e interacciones seleccionada:
m.optimo = lm(formula = csMPa ~ cement + slag + flyash + water + log_age +
cement:log_age + cement:flyash + cement:water, data = df)
summary(m.optimo)
##
## Call:
## lm(formula = csMPa ~ cement + slag + flyash + water + log_age +
## cement:log_age + cement:flyash + cement:water, data = df)
##
## Residuals:
## Min 1Q Median 3Q Max
## -21.8708 -4.3946 -0.1925 4.2548 29.5265
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 8.018e+00 6.596e+00 1.216 0.224385
## cement 1.282e-01 1.963e-02 6.532 1.02e-10 ***
## slag 8.555e-02 3.209e-03 26.655 < 2e-16 ***
## flyash 3.693e-02 1.080e-02 3.420 0.000652 ***
## water -2.252e-01 3.469e-02 -6.492 1.32e-10 ***
## log_age 9.218e+00 5.750e-01 16.033 < 2e-16 ***
## cement:log_age -1.648e-03 1.821e-03 -0.905 0.365706
## cement:flyash 1.051e-04 3.942e-05 2.667 0.007781 **
## cement:water -9.288e-05 1.055e-04 -0.881 0.378740
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 7.2 on 1021 degrees of freedom
## Multiple R-squared: 0.8157, Adjusted R-squared: 0.8143
## F-statistic: 564.9 on 8 and 1021 DF, p-value: < 2.2e-16
Nuestra variable de interés csMPa está medida en MPa
(Megapascals). Los coeficientes del modelo pueden interpretarse
como:
csMPa cuando todas las covariables
son cero. En este contexto, el intercepto no tiene una interpretación
física directa (no es realista tener cero edad ni cero componentes),
pero es necesario para ajustar el modelo.cement = 0.1282):
slag,
flyash, water y log_age), un
aumento de 1 kg/m³ de cemento se asocia con un incremento promedio de
0.1282 MPa en csMPa.slag = 0.08555):
slag se asocia con un
incremento promedio de 0.08555 MPa en la resistencia, manteniendo
constantes las demás variables.flyash = 0.03693):
flyash, se asocia con un
incremento promedio de 0.03693 MPa en la resistencia, manteniendo
constantes las demás covariables.water = -0.2252):
csMPa disminuye en
promedio 0.2252 MPa.log_age = 9.218):
log_age (lo cual equivale
aproximadamente a multiplicar la edad por 2.718) se asocia con un
incremento promedio de 9.218 MPa en csMPa, manteniendo
constantes las demás variables.cement:log_age (p =
0.3657):
cement:flyash (p =
0.00778):
cement:water (p =
0.3787):
En general, los valores-p del summary(m.optimo) permiten
decidir qué efectos son estadísticamente significativos (por ejemplo,
con nivel de significancia 0.05), y el signo de cada coeficiente indica
el sentido de la asociación (positivo o negativo).
Una vez ajustado m.optimo, es fundamental evaluar:
Bondad de ajuste global.
Supuestos del modelo lineal: linealidad, homocedasticidad, normalidad de residuos e independencia.
Presencia de multicolinealidad y valores influyentes.
summary(m.optimo)
##
## Call:
## lm(formula = csMPa ~ cement + slag + flyash + water + log_age +
## cement:log_age + cement:flyash + cement:water, data = df)
##
## Residuals:
## Min 1Q Median 3Q Max
## -21.8708 -4.3946 -0.1925 4.2548 29.5265
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 8.018e+00 6.596e+00 1.216 0.224385
## cement 1.282e-01 1.963e-02 6.532 1.02e-10 ***
## slag 8.555e-02 3.209e-03 26.655 < 2e-16 ***
## flyash 3.693e-02 1.080e-02 3.420 0.000652 ***
## water -2.252e-01 3.469e-02 -6.492 1.32e-10 ***
## log_age 9.218e+00 5.750e-01 16.033 < 2e-16 ***
## cement:log_age -1.648e-03 1.821e-03 -0.905 0.365706
## cement:flyash 1.051e-04 3.942e-05 2.667 0.007781 **
## cement:water -9.288e-05 1.055e-04 -0.881 0.378740
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 7.2 on 1021 degrees of freedom
## Multiple R-squared: 0.8157, Adjusted R-squared: 0.8143
## F-statistic: 564.9 on 8 and 1021 DF, p-value: < 2.2e-16
AIC(m.optimo)
## [1] 7000.523
BIC(m.optimo)
## [1] 7049.896
par(mfrow = c(2, 2))
plot(m.optimo)
par(mfrow = c(1, 1))
residuos_modelo <- residuals(m.optimo)
shapiro.test(residuos_modelo)
##
## Shapiro-Wilk normality test
##
## data: residuos_modelo
## W = 0.99494, p-value = 0.001631
Dado que el modelo incluye términos de interacción, el cálculo estándar del VIF (que evalúa cada término del modelo por separado) puede llevar a interpretaciones erróneas. En presencia de interacciones, los efectos principales y sus términos interactuados están matemáticamente relacionados, por lo que no es adecuado evaluar su colinealidad de manera independiente. Por esta razón, se empleó la opción type = “predictor”, que agrupa correctamente todos los términos asociados a cada predictor original y permite cuantificar la multicolinealidad de forma coherente y consistente con la estructura del modelo.
vif(m.optimo, type = "predictor")
## GVIFs computed for predictors
## GVIF Df GVIF^(1/(2*Df)) Interacts With
## cement 1.522042 7 1.030458 log_age, flyash, water
## slag 1.522042 1 1.233711 --
## flyash 120.885445 3 2.223629 cement
## water 11.773781 3 1.508294 cement
## log_age 85.632858 3 2.099456 cement
## Other Predictors
## cement slag
## slag cement, flyash, water, log_age
## flyash slag, water, log_age
## water slag, flyash, log_age
## log_age slag, flyash, water
Al evaluar la colinealidad mediante el GVIF ajustado para modelos con interacciones, todos los predictores presentan valores inferiores a 3, lo cual indica ausencia de colinealidad severa. Las variables flyash y log_age muestran una colinealidad moderada asociada a sus interacciones con cement, pero permanecen dentro de niveles aceptables para su interpretación.
Finalmente, se utiliza el modelo ajustado para realizar predicciones de la resistencia para nuevas mezclas de concreto, y se calculan:
Intervalos de confianza para la media de csMPa.
Intervalos de predicción para observaciones individuales.
nuevos_datos <- data.frame(
cement = c(300, 450, 250),
slag = c(100, 0, 50),
flyash = c(0, 75, 0),
water = c(180, 165, 170),
age = c(7, 28, 90)
)
nuevos_datos$log_age <- log(nuevos_datos$age)
Cada fila de nuevos_datos representa un diseño de mezcla distinto (cantidades de cemento, escoria, ceniza, agua y edad de curado). ## 4.2 Intervalos de confianza para la media
pred_conf <- predict(m.optimo,
newdata = nuevos_datos,
interval = "confidence",
level = 0.95)
print(cbind(nuevos_datos, pred_conf))
## cement slag flyash water age log_age fit lwr upr
## 1 300 100 0 180 7 1.945910 26.46771 25.70337 27.23205
## 2 450 0 75 165 28 3.332205 56.23403 54.87643 57.59164
## 3 250 50 0 170 90 4.499810 41.74955 40.60742 42.89167
pred_pred <- predict(m.optimo,
newdata = nuevos_datos,
interval = "prediction",
level = 0.95)
print(cbind(nuevos_datos, pred_pred))
## cement slag flyash water age log_age fit lwr upr
## 1 300 100 0 180 7 1.945910 26.46771 12.31896 40.61646
## 2 450 0 75 165 28 3.332205 56.23403 42.04087 70.42720
## 3 250 50 0 170 90 4.499810 41.74955 27.57537 55.92373