A. Introducción

Los aumentos salariales pueden influir en la motivación, la permanencia y la percepción de reconocimiento de los empleados. Desde la gestión humana, es relevante estudiar si los incrementos se relacionan principalmente con las evaluaciones de rendimiento, con los años que una persona lleva en la organización o con el hecho de realizar horas extra. Identificar patrones ayudaría a plantear preguntas sobre la coherencia de la política de aumentos y sobre los límites de las predicciones basadas en datos.

Se utiliza la Base 3 de personal, suministrada en el curso, que contiene 1.470 registros de una empresa. Nuestro objetivo no es recomendar automáticamente el aumento de un empleado, sino evaluar tres regresiones lineales simples que permitan estimar el porcentaje del último aumento salarial. Como insiste la guía, nos preguntamos no solo si existe una relación estadística, sino si el modelo sería suficientemente confiable y útil para tomar una decisión real.

El análisis corresponde a datos de empleados en un mismo conjunto, no a una serie temporal. Por ello, nuestras predicciones son comparaciones entre perfiles y no pronósticos de aumentos futuros en una fecha específica. Tampoco podemos establecer relaciones causales a partir de estas asociaciones.

B. Punto 1. Exploración y regresión lineal simple

1. Problema, variables e hipótesis

Pregunta de investigación: ¿Cuál de las variables rendimiento laboral, antigüedad en la empresa y realización de horas extra permite explicar y predecir mejor el porcentaje del último aumento salarial?

Decisión empresarial que podría apoyar: revisar si los porcentajes de aumento observados muestran patrones asociados al rendimiento y explorar si la antigüedad o las horas extra aportan información útil para un análisis salarial inicial. La empresa no debería usar estos resultados como una regla automática de remuneración.

Papel Variable de la base Unidad / codificación Justificación de su elección
Dependiente (Y) Porcentaje_aumento_salarial Porcentaje del último aumento Es la magnitud que se desea explicar y predecir.
Independiente X1 Rendimiento_Laboral Calificación de rendimiento; en los registros aparecen solo 3 y 4 Permite examinar si empleados con mejor evaluación reciben aumentos mayores.
Independiente X2 Antiguedad Años en la empresa Permite contrastar si la permanencia está relacionada con el incremento salarial.
Independiente X3 Horas_Extra Categórica binaria: No / Si Permite comparar el porcentaje de aumento entre quienes reportan realizar horas extra y quienes no.

Hipótesis: esperamos una relación positiva entre rendimiento y aumento salarial. Para antigüedad y horas extra no asumimos que exista una asociación: las incluimos para comprobar si el aumento parece premiar la permanencia o el esfuerzo adicional medido de forma limitada. Cada modelo contrasta H0: beta1 = 0 frente a H1: beta1 != 0, con un nivel de significancia del 5 %.

Las regresiones simples son tres análisis separados, con la misma Y y una X distinta en cada uno. La regresión múltiple se reserva para el Punto 2 del caso.

2. Importación, calidad de la base y atípicos

# Ubicar el Excel tanto al compilar con Knit como al ejecutar bloques en RStudio.
# Al abrir el archivo .Rproj incluido, getwd() sera la carpeta del proyecto.
directorios <- getwd()
if (requireNamespace("rstudioapi", quietly=TRUE) && rstudioapi::isAvailable()) {
  ruta_editor <- tryCatch(rstudioapi::getActiveDocumentContext()$path,
                          error=function(e) "")
  if (nzchar(ruta_editor)) directorios <- c(directorios, dirname(ruta_editor))
  ruta_proyecto <- tryCatch(rstudioapi::getActiveProject(),
                            error=function(e) NULL)
  if (!is.null(ruta_proyecto)) directorios <- c(directorios, ruta_proyecto)
}
directorios <- unique(normalizePath(directorios, winslash="/", mustWork=FALSE))
posibles_archivos <- unique(c(
  file.path(directorios, "base3_ingreso.xlsx"),
  file.path(directorios, "datos", "base3_ingreso.xlsx")
))
encontrados <- posibles_archivos[file.exists(posibles_archivos)]
if (length(encontrados)==0) {
  stop(paste0("No se encontro base3_ingreso.xlsx. Abra el archivo ",
              "Punto_1_Aumentos_Salariales.Rproj desde la carpeta EXTRAIDA del ZIP. ",
              "Carpeta de trabajo actual: ", getwd()))
}
archivo <- encontrados[1]
cat("Leyendo base de datos desde: ", archivo, "\n")
## Leyendo base de datos desde:  C:/Users/JUANDI/OneDrive/Escritorio/caso 2/base3_ingreso.xlsx
original <- readxl::read_excel(archivo, sheet="Base")
datos <- data.frame(
  Aumento = as.numeric(original[["Porcentaje_aumento_salarial"]]),
  Rendimiento = as.numeric(original[["Rendimiento_Laboral"]]),
  Antiguedad = as.numeric(original[["Antiguedad"]]),
  Horas_Extra = factor(trimws(as.character(original[["Horas_Extra"]])),
                       levels=c("No","Si"))
)
if (any(!complete.cases(datos))) {
  stop("Hay registros incompletos en las variables elegidas: revisar antes de modelar")
}
calidad <- data.frame(
  Indicador=c("Empleados", "Variables originales", "Faltantes en el archivo original",
              "Filas duplicadas exactas", "Registros completos del análisis",
              "Antigüedad mayor que experiencia total",
              "Años desde la promoción mayores que antigüedad"),
  Resultado=c(nrow(original), ncol(original), sum(is.na(original)),
              sum(duplicated(original)), sum(complete.cases(datos)),
              sum(original[["Antiguedad"]] > original[["Años_Experiencia"]], na.rm=TRUE),
              sum(original[["Años_ultima_promoción"]] > original[["Antiguedad"]], na.rm=TRUE))
)
knitr::kable(calidad, caption="Revisión de calidad e inconsistencias")
Revisión de calidad e inconsistencias
Indicador Resultado
Empleados 1470
Variables originales 24
Faltantes en el archivo original 0
Filas duplicadas exactas 0
Registros completos del análisis 1470
Antigüedad mayor que experiencia total 0
Años desde la promoción mayores que antigüedad 0

La revisión identificó 1470 registros, 0 faltantes y 0 duplicados exactos. No se encontraron los dos tipos de inconsistencia temporal comprobados en la tabla. No fue necesario imputar o eliminar filas por esas razones. Es importante recordar que la ausencia de problemas detectados no garantiza que los datos sean representativos de otras empresas.

limites <- function(z) {
  q <- quantile(z, c(.25,.75))
  c(inferior=unname(q[1]-1.5*(q[2]-q[1])),
    superior=unname(q[2]+1.5*(q[2]-q[1])))
}
regla_y <- limites(datos$Aumento)
regla_ant <- limites(datos$Antiguedad)
atip_y <- sum(datos$Aumento < regla_y[1] | datos$Aumento > regla_y[2])
atip_ant <- sum(datos$Antiguedad < regla_ant[1] | datos$Antiguedad > regla_ant[2])
tabla_atip <- data.frame(
  Variable=c("Aumento salarial (%)", "Antigüedad (años)"),
  Límite_inferior=c(regla_y[1],regla_ant[1]),
  Límite_superior=c(regla_y[2],regla_ant[2]),
  Observaciones_fuera=c(atip_y,atip_ant))
knitr::kable(tabla_atip, digits=1, caption="Revisión con la regla del rango intercuartílico")
Revisión con la regla del rango intercuartílico
Variable Límite_inferior Límite_superior Observaciones_fuera
Aumento salarial (%) 3 27 0
Antigüedad (años) -6 18 104

El porcentaje de aumento está entre 11 % y 25 %; la regla intercuartílica no marca aumentos extremos. En antigüedad señala 104 casos con trayectoria superior a 18 años; se conservaron porque una mayor permanencia puede ser real y no se encontró evidencia de error en esos registros. No aplicamos la regla intercuartílica al rendimiento, pues solo hay dos calificaciones observadas (3 y 4) y el criterio marcaría como “atípicos” a todos los empleados con 4 sin justificación válida. Tampoco corresponde aplicarla a horas extra por ser categórica.

3. Análisis exploratorio

describir <- function(z) c(N=length(z), Minimo=min(z), Q1=unname(quantile(z,.25)),
                         Mediana=median(z), Promedio=mean(z),
                         Q3=unname(quantile(z,.75)), Maximo=max(z), DE=sd(z))
tabla_desc <- t(sapply(datos[c("Aumento","Rendimiento","Antiguedad")], describir))
knitr::kable(round(tabla_desc,2), caption="Estadísticas descriptivas principales")
Estadísticas descriptivas principales
N Minimo Q1 Mediana Promedio Q3 Maximo DE
Aumento 1470 11 12 14 15.21 18 25 3.66
Rendimiento 1470 3 3 3 3.15 3 4 0.36
Antiguedad 1470 0 3 5 7.01 9 40 6.13
knitr::kable(as.data.frame(table(Rendimiento=datos$Rendimiento)),
             caption="Distribución de evaluaciones laborales")
Distribución de evaluaciones laborales
Rendimiento Freq
3 1244
4 226
knitr::kable(as.data.frame(table(Horas_Extra=datos$Horas_Extra)),
             caption="Distribución de horas extra")
Distribución de horas extra
Horas_Extra Freq
No 1054
Si 416

El porcentaje de aumento tiene un promedio de 15,21 % y una mediana de 14 %. La antigüedad media es 7,01 años. Un dato esencial es que, aunque la escala de rendimiento se presenta como una calificación, esta base contiene únicamente los niveles 3 y 4, por lo que no es válido extrapolar resultados a evaluaciones 1, 2 o 5.

hist(datos$Aumento, breaks=seq(10.5,25.5,1), col="#D6E9E6", border="white",
     main="Distribución de aumentos salariales", xlab="Aumento salarial (%)",
     ylab="Número de empleados")
abline(v=median(datos$Aumento), col="#AF672F", lwd=2, lty=2)
legend("topright", legend="Mediana", col="#AF672F", lwd=2,lty=2,bty="n")
Distribución del porcentaje del último aumento salarial

Distribución del porcentaje del último aumento salarial

4. Correlaciones, dispersión y comparaciones entre grupos

El rendimiento solo tiene dos categorías numéricas observadas (3/4). Su correlación con el aumento puede calcularse con Pearson y, por tener dos niveles, equivale en magnitud a una correlación punto-biserial. Para horas extra usamos la codificación No = 0, Si = 1: es más informativo interpretarla como una comparación entre grupos que como una variable numérica continua.

horas01 <- as.numeric(datos$Horas_Extra=="Si")
cp <- cor.test(datos$Aumento, datos$Rendimiento)
ct <- cor.test(datos$Aumento, datos$Antiguedad)
ch <- cor.test(datos$Aumento, horas01)
resumen_cor <- data.frame(
  Relacion=c("Aumento vs. rendimiento (3/4)",
             "Aumento vs. antigüedad", "Aumento vs. horas extra (0/1)"),
  Correlacion=c(unname(cp$estimate), unname(ct$estimate), unname(ch$estimate)),
  P_valor=c(fmt_p(cp$p.value),fmt_p(ct$p.value),fmt_p(ch$p.value)))
knitr::kable(transform(resumen_cor,Correlacion=round(Correlacion,4)),
             caption="Tres correlaciones del aumento salarial con los predictores")
Tres correlaciones del aumento salarial con los predictores
Relacion Correlacion P_valor
Aumento vs. rendimiento (3/4) 0.7735 < 0,0001
Aumento vs. antigüedad -0.0360 0,1678
Aumento vs. horas extra (0/1) -0.0054 0,8351
set.seed(2026)
plot(jitter(datos$Rendimiento, amount=.14), datos$Aumento, pch=16,
     col=grDevices::adjustcolor("#147F83",alpha.f=.24),
     xlab="Calificación de rendimiento", ylab="Aumento salarial (%)",
     main="Rendimiento y aumento", xaxt="n", xlim=c(2.6,4.4))
axis(1,at=c(3,4),labels=c("3","4"))
rect(2.9,mean(datos$Aumento[datos$Rendimiento==3])-.10,
     3.1,mean(datos$Aumento[datos$Rendimiento==3])+.10,
     col="#B66F32",border=NA)
rect(3.9,mean(datos$Aumento[datos$Rendimiento==4])-.10,
     4.1,mean(datos$Aumento[datos$Rendimiento==4])+.10,
     col="#B66F32",border=NA)
Aumento por nivel de rendimiento: puntos y media por grupo

Aumento por nivel de rendimiento: puntos y media por grupo

plot(datos$Antiguedad, datos$Aumento, pch=16,
     col=grDevices::adjustcolor("#147F83",alpha.f=.25),
     xlab="Antigüedad (años)", ylab="Aumento salarial (%)",
     main="Antigüedad y aumento")
abline(lm(Aumento~Antiguedad,data=datos),col="#B66F32",lwd=2)
Dispersión entre años en la empresa y porcentaje de aumento

Dispersión entre años en la empresa y porcentaje de aumento

set.seed(2026)
plot(jitter(as.numeric(datos$Horas_Extra),amount=.16),datos$Aumento,
     xaxt="n",xlim=c(.55,2.45),pch=16,
     col=grDevices::adjustcolor("#147F83",alpha.f=.25),
     xlab="Horas extra", ylab="Aumento salarial (%)",
     main="Horas extra y aumento")
axis(1,at=c(1,2),labels=c("No","Si"))
Comparación de aumentos entre empleados con y sin horas extra

Comparación de aumentos entre empleados con y sin horas extra

grupo_r <- aggregate(Aumento~Rendimiento,data=datos, FUN=function(z) c(N=length(z),Promedio=mean(z),Min=min(z),Max=max(z)))
tab_r <- data.frame(Rendimiento=grupo_r$Rendimiento,
                    N=grupo_r$Aumento[,"N"],
                    Promedio=round(grupo_r$Aumento[,"Promedio"],2),
                    Minimo=grupo_r$Aumento[,"Min"], Maximo=grupo_r$Aumento[,"Max"])
knitr::kable(tab_r,caption="Porcentaje de aumento según la evaluación")
Porcentaje de aumento según la evaluación
Rendimiento N Promedio Minimo Maximo
3 1244 14.00 11 19
4 226 21.85 20 25
tab_h <- aggregate(Aumento~Horas_Extra,data=datos,mean)
knitr::kable(tab_h,digits=3,caption="Aumento promedio según horas extra")
Aumento promedio según horas extra
Horas_Extra Aumento
No 15.222
Si 15.178

La asociación rendimiento-aumento es positiva y fuerte (r = 0,774), mientras que la antigüedad tiene una correlación muy pequeña y negativa (r = -0,036) y las horas extra prácticamente no presentan relación (r = -0,005). Sorprende que los aumentos para rendimiento 3 van de 11 % a 19 %, mientras que para rendimiento 4 van de 20 % a 25 %: los intervalos no se superponen. Esto sugiere una posible política de incrementos fuertemente vinculada a la evaluación, aunque no sabemos cómo se diseñó o generó la información.

5. Tres regresiones lineales simples e interpretación

Los tres modelos tienen como respuesta Aumento, medido en porcentaje. Por ello, un coeficiente estimado de 1,00 significa una diferencia de un punto porcentual, no un incremento de 1 % relativo sobre el porcentaje anterior.

  • Modelo 1: aumento ~ rendimiento. La diferencia de la calificación 3 a la 4 se interpreta como la diferencia entre las medias de ambos grupos.
  • Modelo 2: aumento ~ antigüedad. La pendiente estima el cambio promedio en puntos porcentuales por cada año adicional.
  • Modelo 3: aumento ~ horas extra. La referencia es No; el coeficiente para Si representa la diferencia de medias Si menos No.
m1 <- lm(Aumento~Rendimiento,data=datos)
m2 <- lm(Aumento~Antiguedad,data=datos)
m3 <- lm(Aumento~Horas_Extra,data=datos)
extraer <- function(mod,nombre) {
  cf <- summary(mod)$coefficients
  data.frame(Modelo=nombre, Intercepto=unname(coef(mod)[1]),
             Coeficiente=unname(coef(mod)[2]), R2=summary(mod)$r.squared,
             P_valor=fmt_p(cf[2,4]))
}
tabla_modelos <- rbind(extraer(m1,"1. Rendimiento"),
                       extraer(m2,"2. Antigüedad"),
                       extraer(m3,"3. Horas extra"))
tabla_modelos$Intercepto <- round(tabla_modelos$Intercepto,4)
tabla_modelos$Coeficiente <- round(tabla_modelos$Coeficiente,4)
tabla_modelos$R2 <- round(tabla_modelos$R2,4)
knitr::kable(tabla_modelos, caption="Coeficientes, R² y significancia al 5 %")
Coeficientes, R² y significancia al 5 %
Modelo Intercepto Coeficiente R2 P_valor
1. Rendimiento -9.5358 7.8463 0.5984 < 0,0001
2. Antigüedad 15.3602 -0.0215 0.0013 0,1678
3. Horas extra 15.2220 -0.0441 0.0000 0,8351

Modelo 1, rendimiento. Su coeficiente es 7,846 puntos porcentuales, es decir, los empleados evaluados con 4 tienen en promedio ese aumento adicional frente a los evaluados con 3. El modelo explica 59,84 % de la variación observada y el coeficiente es estadísticamente significativo (p < 0,0001). El intercepto no debe interpretarse como un aumento para calificación 0, ya que ese nivel no aparece en la base.

Modelo 2, antigüedad. La pendiente es -0,0215 puntos porcentuales por año, casi nula. El R² es 0,130 % y p = 0,168. Al 5 % no encontramos evidencia suficiente de una asociación lineal individual entre años de antigüedad y porcentaje de aumento.

Modelo 3, horas extra. Los empleados que reportan horas extra tienen un aumento promedio -0,044 puntos porcentuales distinto al grupo No. La diferencia es mínima y no significativa (p = 0,835). Esto no demuestra que las horas extra no impliquen esfuerzo ni que deban generar automáticamente un mayor aumento; solo muestra que esta variable binaria no predice bien el incremento dentro de esta base.

6. Validación de supuestos y transformaciones

Revisamos los residuos frente a los valores predichos, la normalidad aproximada (Shapiro-Wilk) y la constancia de su variación (Breusch-Pagan mediante una regresión auxiliar). Estas pruebas deben interpretarse con los gráficos y con prudencia, especialmente cuando la respuesta es discreta y el predictor principal solo tiene dos grupos.

prueba_bp <- function(mod) {
  aux <- lm(I(resid(mod)^2) ~ fitted(mod))
  pchisq(length(resid(mod))*summary(aux)$r.squared,df=1,lower.tail=FALSE)
}
mods <- list(m1,m2,m3)
supuestos <- data.frame(
  Modelo=c("1. Rendimiento","2. Antigüedad","3. Horas extra"),
  Shapiro_p=sapply(mods,function(m) fmt_p(shapiro.test(resid(m))$p.value)),
  Breusch_Pagan_p=sapply(mods,function(m) fmt_p(prueba_bp(m))))
knitr::kable(supuestos,caption="Diagnóstico de normalidad y varianza constante de residuos")
Diagnóstico de normalidad y varianza constante de residuos
Modelo Shapiro_p Breusch_Pagan_p
1. Rendimiento < 0,0001 < 0,0001
2. Antigüedad < 0,0001 0,0595
3. Horas extra < 0,0001 0,3658
par(mfrow=c(1,2),mar=c(4,4,3,1))
plot(jitter(fitted(m1),amount=.15),resid(m1),pch=16,
     col=grDevices::adjustcolor("#147F83",alpha.f=.25),
     xlab="Aumento predicho (%)",ylab="Residuo (puntos porcentuales)",
     main="Residuos vs. ajustados")
abline(h=0,col="#B66F32",lwd=2)
qqnorm(resid(m1),pch=16,col=grDevices::adjustcolor("#147F83",alpha.f=.25),
       main="Normalidad: Q-Q")
qqline(resid(m1),col="#B66F32",lwd=2)
Modelo de rendimiento: residuos frente a predicción y gráfico Q-Q

Modelo de rendimiento: residuos frente a predicción y gráfico Q-Q

par(mfrow=c(1,1))

El modelo de rendimiento no cumple plenamente las condiciones clásicas de normalidad y varianza constante: Shapiro-Wilk entrega p < 0,0001 y Breusch-Pagan p < 0,0001. Esto puede afectar inferencias y bandas de incertidumbre basadas en los supuestos clásicos. Aun así, el error fuera de muestra es una forma más directa de evaluar la utilidad predictiva. No eliminamos observaciones arbitrariamente para forzar pruebas favorables.

Probamos una transformación logarítmica del porcentaje de aumento solo como análisis exploratorio. Su utilidad se compara mediante el error después de retransformar las predicciones a porcentaje, nunca comparando directamente el R² en escalas diferentes.

mlog <- lm(log(Aumento)~Rendimiento,data=datos)
knitr::kable(data.frame(Modelo="Log(aumento) ~ rendimiento",
                        R2_en_escala_log=round(summary(mlog)$r.squared,4),
                        Shapiro_p=fmt_p(shapiro.test(resid(mlog))$p.value),
                        BP_p=fmt_p(prueba_bp(mlog))),
             caption="Transformación exploratoria: diagnóstico en la escala logarítmica")
Transformación exploratoria: diagnóstico en la escala logarítmica
Modelo R2_en_escala_log Shapiro_p BP_p
Log(aumento) ~ rendimiento 0.522 < 0,0001 < 0,0001

7. Validación cruzada, error de pronóstico y comparación

Siguiendo la guía, evaluamos los modelos con validación cruzada de cinco particiones, iguales para los tres modelos. El archivo no contiene una dimensión temporal que exija separar entrenamiento y prueba por fechas. Para una evaluación reproducible, cada quinto registro se asigna a la misma partición y en cada vuelta se entrena con cuatro partes y se evalúa en la restante. Se comparan los errores con una referencia sencilla: predecir la mediana del grupo de entrenamiento.

El MAE es el promedio de los errores absolutos entre los aumentos reales y los estimados. Aquí su unidad es puntos porcentuales (pp): si se predice un aumento de 17 % y el real fue 15 %, el error absoluto es 2 pp.

fold <- rep(1:5,length.out=nrow(datos))
formulas <- list("1. Rendimiento"=Aumento~Rendimiento,
                 "2. Antigüedad"=Aumento~Antiguedad,
                 "3. Horas extra"=Aumento~Horas_Extra)
cv_predict <- function(formula,datos,fold) {
  pred <- rep(NA_real_,nrow(datos))
  for (k in 1:5) {
    train <- datos[fold!=k,,drop=FALSE]
    test <- datos[fold==k,,drop=FALSE]
    ajuste <- lm(formula,data=train)
    pred[fold==k] <- predict(ajuste,newdata=test)
  }
  pred
}
mae <- function(real,pred) mean(abs(real-pred))
mae_modelos <- sapply(formulas,function(f) mae(datos$Aumento,cv_predict(f,datos,fold)))
pred_base <- rep(NA_real_,nrow(datos))
pred_log <- rep(NA_real_,nrow(datos))
for (k in 1:5) {
  train <- datos[fold!=k,,drop=FALSE]
  test <- datos[fold==k,,drop=FALSE]
  pred_base[fold==k] <- median(train$Aumento)
  modlog <- lm(log(Aumento)~Rendimiento,data=train)
  factor_smear <- mean(exp(resid(modlog)))
  pred_log[fold==k] <- exp(predict(modlog,newdata=test))*factor_smear
}
maes <- c(mae_modelos, "4. Log-rendimiento (retransformado)"=mae(datos$Aumento,pred_log),
          "Referencia: mediana"=mae(datos$Aumento,pred_base))
tab_mae <- data.frame(Modelo=names(maes),
                      MAE_pp=round(as.numeric(maes),4),
                      Mejora_vs_mediana=round(100*(1-as.numeric(maes)/maes["Referencia: mediana"]),2))
knitr::kable(tab_mae,caption="MAE mediante validación cruzada (puntos porcentuales)")
MAE mediante validación cruzada (puntos porcentuales)
Modelo MAE_pp Mejora_vs_mediana
1. Rendimiento 1.8843 34.79
2. Antigüedad 3.0540 -5.68
3. Horas extra 3.0590 -5.85
4. Log-rendimiento (retransformado) 1.8843 34.80
Referencia: mediana 2.8898 0.00

El modelo de rendimiento obtiene un MAE de 1,884 puntos porcentuales, frente a 2,890 pp del modelo de referencia: una mejora de 34,8 % en error absoluto. Antigüedad y horas extra no mejoran la referencia de la mediana, por lo que no se justificaría elegirlos individualmente para esta predicción.

La transformación logarítmica produce un MAE de 1,8843 pp, frente a 1,8843 pp del modelo original. La diferencia es mínima; preferimos el modelo sin transformar porque se interpreta fácilmente en puntos porcentuales, y no hay una mejora predictiva relevante.

Predicciones ilustrativas del modelo más útil

escenarios <- data.frame(Rendimiento=c(3,4))
escenarios$Aumento_esperado_porcentaje <- round(predict(m1,newdata=escenarios),2)
knitr::kable(escenarios,caption="Aumentos estimados según calificación observada")
Aumentos estimados según calificación observada
Rendimiento Aumento_esperado_porcentaje
3 14.00
4 21.85

Estas predicciones reproducen las medias de ambos grupos. No son una recomendación de incrementos individuales ni deben extrapolarse a evaluaciones 1, 2 o 5. El margen medio de error sigue siendo significativo para decidir el aumento exacto de una persona.

8. Conclusiones y utilidad para la empresa

Hallazgo central: la evaluación del rendimiento es el predictor individual claramente más informativo para explicar el porcentaje del último aumento salarial. Es estadísticamente significativa, explica cerca del 59,8 % de las diferencias y logra el menor error fuera de muestra. Por contraste, la antigüedad y las horas extra no presentan asociaciones lineales relevantes en este análisis ni superan la mediana como referencia de predicción.

¿Lo utilizaríamos para tomar decisiones reales? Sí, solo como herramienta exploratoria de auditoría de patrones de aumentos. No sería suficiente para fijar incrementos de forma automática: la base solo contiene calificaciones de rendimiento 3/4, los porcentajes de aumento son discretos, el diagnóstico de residuos detecta problemas y se desconoce cómo la empresa decidió o registró estos porcentajes. Además, los rangos de aumentos por rendimiento no se traslapan (3: 11–19 %; 4: 20–25 %), lo que podría reflejar una regla preestablecida de aumentos asociada a la evaluación. Sin conocer el proceso de construcción de las variables, no puede descartarse una vinculación casi mecánica entre ellas; así, una asociación fuerte no necesariamente aporta información nueva para decidir.

Interpretación responsable: que antigüedad y horas extra tengan baja capacidad explicativa no demuestra que los empleados antiguos o quienes trabajan horas adicionales merezcan un menor reconocimiento. Tampoco se puede hablar de justicia salarial sin considerar cargo, nivel, responsabilidades, resultados y contexto. Para decisiones individuales se requerirían esas variables, reglas institucionales y validación adicional con datos posteriores.

Respuesta a la pregunta central de la guía: el mejor modelo simple es útil para describir un patrón y estimar un aumento aproximado dentro de los niveles observados, pero no es suficientemente confiable ni completo como única base para asignar incrementos. Un modelo puede ofrecer un R² alto y seguir siendo limitado para decidir correctamente en la realidad.

Fuente: archivo base3_ingreso.xlsx, Base 3 suministrada con el Caso 2 de la asignatura Análisis predictivo y visualización. Cálculos originales en R; avance correspondiente únicamente al Punto 1, sin regresión múltiple.