Teoría Regresión cuantilíca
La regresión cuantílica (Quantile Regression) es una técnica
estadística que permite modelar la relación entre una variable
dependiente y una o más variables independientes en distintos puntos de
la distribución condicional de la variable dependiente.
¿Por qué usar Quantile
Regression?
- Permite obtener intervalos de predicción, lo cual es útil para la
toma de decisiones en negocios.
- A diferencia de los métodos no lineales tradicionales de aprendizaje
supervisado, ofrece una forma explícita de obtener intervalos de
predicción.
- Mejora la precisión en comparación con el uso de intervalos de
predicción basados en regresión lineal estándar.
¿Para qué sirve la Quantile
Regression?
Es útil para analizar distribuciones asimétricas y detectar
efectos diferenciados en distintos niveles.
Proporciona una mejor comprensión de la heterogeneidad en los
datos.
Es robusta a valores atípicos, ya que minimiza una función de
pérdida asimétrica.
Se usa en análisis económico, modelos de riesgo, bioestadística y
otras aplicaciones donde la variabilidad es clave.
Permite modelar relaciones no capturadas por la regresión lineal
ordinaria.
Es aplicable cuando la relación entre las variables cambia en
distintos puntos de la distribución.
Diferencias clave entre OLS y Quantile
Regression
OLS (Regresión Lineal Ordinaria): Minimiza el
error cuadrático medio (MSE) y modela la media condicional.
Quantile Regression: Minimiza una función de
pérdida ponderada, lo que permite estimar distintos cuantiles.
Robustez: Quantile Regression es menos sensible
a valores atípicos que OLS.
Flexibilidad: Mientras OLS asume
homocedasticidad (varianza constante del error), Quantile Regression
permite heterocedasticidad.
Ejemplos de Aplicación
- Economía: Evaluación de desigualdad en ingresos,
determinando cómo factores afectan diferentes niveles salariales.
- Finanzas: Modelado de riesgos en mercados
financieros.
- Medicina: Análisis de percentiles en medidas
biomédicas como presión arterial o peso infantil.
- Ciencias sociales: Evaluación de impacto de
políticas en distintos grupos poblacionales.
Cargar las líbrerias
necesarias
#install.packages("quantreg")
library(quantreg)
#install.packages("ggplot")
library(ggplot2)
Descripción del Análisis
En este ejemplo, usaremos Quantile Regression para analizar el
impacto del peso del auto (wt)en el consumo de combustible (mpg) usando
el dataset mtcars.
Cargar datos (mtcars)
#Esta base de datos viene ya dentro de R
data(mtcars)
Revisar las primeras filas del
dataset
## mpg cyl disp hp drat wt qsec vs am gear carb
## Mazda RX4 21.0 6 160 110 3.90 2.620 16.46 0 1 4 4
## Mazda RX4 Wag 21.0 6 160 110 3.90 2.875 17.02 0 1 4 4
## Datsun 710 22.8 4 108 93 3.85 2.320 18.61 1 1 4 1
## Hornet 4 Drive 21.4 6 258 110 3.08 3.215 19.44 1 0 3 1
## Hornet Sportabout 18.7 8 360 175 3.15 3.440 17.02 0 0 3 2
## Valiant 18.1 6 225 105 2.76 3.460 20.22 1 0 3 1
Definir Variables
df <- mtcars
df$X <- df$wt # Peso del auto
df$y <- df$mpg # Millas por galón
Ajustar un modelo de Quantile
Regression para diferentes cuantiles
quantiles <- c(0.1, 0.5, 0.9) # Percentiles 10, 50 y 90
models <- lapply(quantiles, function(q) rq(y ~ X, tau = q, data = df))
# q representa cada uno de los percetiles
#tau controla qué parte de la distribución condicional estamos modelando.
## Min. 1st Qu. Median Mean 3rd Qu. Max.
## 0.1 0.3 0.5 0.5 0.7 0.9
Ajustar un modelo de Regresión Lineal
estándar para comparación
lm_model <- lm(y ~ X, data = df)
Crear un dataframe para almacenar
predicciones
# Creamos un data frame con una secuencia de valores de X que van desde el mínimo hasta el máximo en df$X
X_seq <- data.frame(X = seq(min(df$X), max(df$X), length.out = 100))
# Crear un nuevo data frame para almacenar las predicciones del modelo de regresión
pred_df <- data.frame(
X = X_seq$X,
OLS = predict(lm_model, newdata = X_seq)
)
Agregar predicciones de regresión
cuantílica
#loop que recorre todos los cuantiles definidos en la variable 'quantiles'
for (i in 1:length(quantiles)) {
pred_df[[paste0("Q", quantiles[i] * 100)]] <- predict(models[[i]], newdata = X_seq)
}
Graficar resultados
plot <- ggplot(data = df, aes(x = X, y = y)) +
geom_point(alpha = 0.5) + # Puntos de datos reales
geom_line(data = pred_df, aes(x = X, y = OLS, color = "OLS"), linetype = "dashed") +
geom_line(data = pred_df, aes(x = X, y = Q10, color = "Quantile 10")) +
geom_line(data = pred_df, aes(x = X, y = Q50, color = "Quantile 50")) +
geom_line(data = pred_df, aes(x = X, y = Q90, color = "Quantile 90")) +
scale_color_manual(values = c("black", "blue", "red", "green")) +
labs(title = "Comparación de Regresión Cuantílica y Lineal",
x = "Peso del Auto (wt)",
y = "Millas por Galón (mpg)",
color = "Modelo") +
theme_minimal()
print(plot)

Explicación
La línea negra discontinua representa la regresión lineal
estándar (OLS).
Las líneas azul, roja y verde representan las regresiones
cuantílicas para los percentiles 10, 50 y 90. *Línea azul (Quantile 10):
Muestra cómo los autos con menor consumo de gasolina (percentil 10)
están afectados por el peso.
*Línea roja (Quantile 50 - Mediana): Representa la relación mediana
entre wt y mpg, equivalente a la regresión cuantílica en el percentil
50.
*Línea verde (Quantile 90): Modela la relación para los autos con
mejor consumo de gasolina (percentil 90).
-OLS subestima o sobreestima en ciertas regiones, ya que solo modela
la media de mpg, mientras que Quantile Regression permite entender cómo
cambia mpg en diferentes niveles.
Referencias
- Ngieng Kianyew, Understanding How Quantile Regression
Works, Medium (2023).
LS0tCnRpdGxlOiAiUXVhbnRpbGUgUmVncmVzc2lvbiIKYXV0aG9yOiAiVml2aWFuYSBEdXLDoW5fIEEwMDgzNzc3NiIKZGF0ZTogIjIwMjUtMDItMjciCm91dHB1dDoKICBodG1sX2RvY3VtZW50OgogICAgdG9jOiBUUlVFCiAgICB0b2NfZmxvYXQ6IFRSVUUKICAgIGNvZGVfZG93bmxvYWQ6IFRSVUUKICAgIHRoZW1lOiBqb3VybmFsCiAgICBoaWdobGlnaHQ6IGhhZGRvY2sKLS0tCgojIDxzcGFuIHN0eWxlPSAiQ29sb3I6IHB1cnBsZTsiPlRlb3LDrWEgUmVncmVzacOzbiBjdWFudGlsw61jYSA8L3NwYW4+CkxhIHJlZ3Jlc2nDs24gY3VhbnTDrWxpY2EgKFF1YW50aWxlIFJlZ3Jlc3Npb24pIGVzIHVuYSB0w6ljbmljYSBlc3RhZMOtc3RpY2EgcXVlIHBlcm1pdGUgbW9kZWxhciBsYSByZWxhY2nDs24gZW50cmUgdW5hIHZhcmlhYmxlIGRlcGVuZGllbnRlIHkgdW5hIG8gbcOhcyB2YXJpYWJsZXMgaW5kZXBlbmRpZW50ZXMgZW4gZGlzdGludG9zIHB1bnRvcyBkZSBsYSBkaXN0cmlidWNpw7NuIGNvbmRpY2lvbmFsIGRlIGxhIHZhcmlhYmxlIGRlcGVuZGllbnRlLgogCiMjIyA8c3BhbiBzdHlsZT0gIkNvbG9yOiB2aW9sZXQ7Ij7Cv1BvciBxdcOpIHVzYXIgUXVhbnRpbGUgUmVncmVzc2lvbj88L3NwYW4+Ci0gUGVybWl0ZSBvYnRlbmVyIGludGVydmFsb3MgZGUgcHJlZGljY2nDs24sIGxvIGN1YWwgZXMgw7p0aWwgcGFyYSBsYSB0b21hIGRlIGRlY2lzaW9uZXMgZW4gbmVnb2Npb3MuCi0gQSBkaWZlcmVuY2lhIGRlIGxvcyBtw6l0b2RvcyBubyBsaW5lYWxlcyB0cmFkaWNpb25hbGVzIGRlIGFwcmVuZGl6YWplIHN1cGVydmlzYWRvLCBvZnJlY2UgdW5hIGZvcm1hIGV4cGzDrWNpdGEgZGUgb2J0ZW5lciBpbnRlcnZhbG9zIGRlIHByZWRpY2Npw7NuLgotIE1lam9yYSBsYSBwcmVjaXNpw7NuIGVuIGNvbXBhcmFjacOzbiBjb24gZWwgdXNvIGRlIGludGVydmFsb3MgZGUgcHJlZGljY2nDs24gYmFzYWRvcyBlbiByZWdyZXNpw7NuIGxpbmVhbCBlc3TDoW5kYXIuCgojIyMgPHNwYW4gc3R5bGU9ICJDb2xvcjogdmlvbGV0OyI+wr9QYXJhIHF1w6kgc2lydmUgbGEgUXVhbnRpbGUgUmVncmVzc2lvbj88L3NwYW4+Ci0gRXMgw7p0aWwgcGFyYSBhbmFsaXphciBkaXN0cmlidWNpb25lcyBhc2ltw6l0cmljYXMgeSBkZXRlY3RhciBlZmVjdG9zIGRpZmVyZW5jaWFkb3MgZW4gZGlzdGludG9zIG5pdmVsZXMuCgotIFByb3BvcmNpb25hIHVuYSBtZWpvciBjb21wcmVuc2nDs24gZGUgbGEgaGV0ZXJvZ2VuZWlkYWQgZW4gbG9zIGRhdG9zLgotIEVzIHJvYnVzdGEgYSB2YWxvcmVzIGF0w61waWNvcywgeWEgcXVlIG1pbmltaXphIHVuYSBmdW5jacOzbiBkZSBww6lyZGlkYSBhc2ltw6l0cmljYS4KLSBTZSB1c2EgZW4gYW7DoWxpc2lzIGVjb27Ds21pY28sIG1vZGVsb3MgZGUgcmllc2dvLCBiaW9lc3RhZMOtc3RpY2EgeSBvdHJhcyBhcGxpY2FjaW9uZXMgZG9uZGUgbGEgdmFyaWFiaWxpZGFkIGVzIGNsYXZlLgotIFBlcm1pdGUgbW9kZWxhciByZWxhY2lvbmVzIG5vIGNhcHR1cmFkYXMgcG9yIGxhIHJlZ3Jlc2nDs24gbGluZWFsIG9yZGluYXJpYS4KIC0gRXMgYXBsaWNhYmxlIGN1YW5kbyBsYSByZWxhY2nDs24gZW50cmUgbGFzIHZhcmlhYmxlcyBjYW1iaWEgZW4gZGlzdGludG9zIHB1bnRvcyBkZSBsYSBkaXN0cmlidWNpw7NuLgoKIyMjIDxzcGFuIHN0eWxlPSAiQ29sb3I6dmlvbGV0OyI+RGlmZXJlbmNpYXMgY2xhdmUgZW50cmUgT0xTIHkgUXVhbnRpbGUgUmVncmVzc2lvbjwvc3Bhbj4KLSAqKk9MUyAoUmVncmVzacOzbiBMaW5lYWwgT3JkaW5hcmlhKToqKiBNaW5pbWl6YSBlbCBlcnJvciBjdWFkcsOhdGljbyBtZWRpbyAoTVNFKSB5IG1vZGVsYSBsYSBtZWRpYSBjb25kaWNpb25hbC4KCi0gKipRdWFudGlsZSBSZWdyZXNzaW9uOioqIE1pbmltaXphIHVuYSBmdW5jacOzbiBkZSBww6lyZGlkYSBwb25kZXJhZGEsIGxvIHF1ZSBwZXJtaXRlIGVzdGltYXIgZGlzdGludG9zIGN1YW50aWxlcy4KCi0gKipSb2J1c3RlejoqKiBRdWFudGlsZSBSZWdyZXNzaW9uIGVzIG1lbm9zIHNlbnNpYmxlIGEgdmFsb3JlcyBhdMOtcGljb3MgcXVlIE9MUy4KLSAqKkZsZXhpYmlsaWRhZDoqKiBNaWVudHJhcyBPTFMgYXN1bWUgaG9tb2NlZGFzdGljaWRhZCAodmFyaWFuemEgY29uc3RhbnRlIGRlbCBlcnJvciksIFF1YW50aWxlIFJlZ3Jlc3Npb24gcGVybWl0ZSBoZXRlcm9jZWRhc3RpY2lkYWQuCgojIyMgPHNwYW4gc3R5bGU9ICJDb2xvcjogdmlvbGV0OyI+RWplbXBsb3MgZGUgQXBsaWNhY2nDs248L3NwYW4+Ci0gKipFY29ub23DrWE6KiogRXZhbHVhY2nDs24gZGUgZGVzaWd1YWxkYWQgZW4gaW5ncmVzb3MsIGRldGVybWluYW5kbyBjw7NtbyBmYWN0b3JlcyBhZmVjdGFuIGRpZmVyZW50ZXMgbml2ZWxlcyBzYWxhcmlhbGVzLgotICoqRmluYW56YXM6KiogTW9kZWxhZG8gZGUgcmllc2dvcyBlbiBtZXJjYWRvcyBmaW5hbmNpZXJvcy4KLSAqKk1lZGljaW5hOioqIEFuw6FsaXNpcyBkZSBwZXJjZW50aWxlcyBlbiBtZWRpZGFzIGJpb23DqWRpY2FzIGNvbW8gcHJlc2nDs24gYXJ0ZXJpYWwgbyBwZXNvIGluZmFudGlsLgotICoqQ2llbmNpYXMgc29jaWFsZXM6KiogRXZhbHVhY2nDs24gZGUgaW1wYWN0byBkZSBwb2zDrXRpY2FzIGVuIGRpc3RpbnRvcyBncnVwb3MgcG9ibGFjaW9uYWxlcy4KCiMgPHNwYW4gc3R5bGU9ICJDb2xvcjogcHVycGxlOyI+Q2FyZ2FyIGxhcyBsw61icmVyaWFzIG5lY2VzYXJpYXM8L3NwYW4+CmBgYHtyIG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0V9CiNpbnN0YWxsLnBhY2thZ2VzKCJxdWFudHJlZyIpCmxpYnJhcnkocXVhbnRyZWcpCiNpbnN0YWxsLnBhY2thZ2VzKCJnZ3Bsb3QiKQpsaWJyYXJ5KGdncGxvdDIpCmBgYAoKIyA8c3BhbiBzdHlsZT0gIkNvbG9yOiBwdXJwbGU7Ij5EZXNjcmlwY2nDs24gZGVsIEFuw6FsaXNpcyA8L3NwYW4+CgpFbiBlc3RlIGVqZW1wbG8sIHVzYXJlbW9zIFF1YW50aWxlIFJlZ3Jlc3Npb24gcGFyYSBhbmFsaXphciBlbCBpbXBhY3RvIGRlbCBwZXNvIGRlbCBhdXRvICh3dCllbiBlbCBjb25zdW1vIGRlIGNvbWJ1c3RpYmxlIChtcGcpIHVzYW5kbyBlbCBkYXRhc2V0IG10Y2Fycy4KCgojIyA8c3BhbiBzdHlsZT0gIkNvbG9yOiB2aW9sZXQ7Ij5DYXJnYXIgZGF0b3MgKG10Y2FycykgPC9zcGFuPgpgYGB7cn0KI0VzdGEgYmFzZSBkZSBkYXRvcyB2aWVuZSB5YSBkZW50cm8gZGUgUgpkYXRhKG10Y2FycykKYGBgCgojIyA8c3BhbiBzdHlsZT0gIkNvbG9yOiB2aW9sZXQ7Ij5SZXZpc2FyIGxhcyBwcmltZXJhcyBmaWxhcyBkZWwgZGF0YXNldDwvc3Bhbj4KCmBgYHtyfQpoZWFkKG10Y2FycykgCmBgYAoKCiMjIDxzcGFuIHN0eWxlPSAiQ29sb3I6IHZpb2xldDsiPkRlZmluaXIgVmFyaWFibGVzPC9zcGFuPgpgYGB7cn0KZGYgPC0gbXRjYXJzCmRmJFggPC0gZGYkd3QgICMgUGVzbyBkZWwgYXV0bwpkZiR5IDwtIGRmJG1wZyAgIyBNaWxsYXMgcG9yIGdhbMOzbgpgYGAKCiMjIDxzcGFuIHN0eWxlPSAiQ29sb3I6IHZpb2xldDsiPkFqdXN0YXIgdW4gbW9kZWxvIGRlIFF1YW50aWxlIFJlZ3Jlc3Npb24gcGFyYSBkaWZlcmVudGVzIGN1YW50aWxlczwvc3Bhbj4KYGBge3J9CnF1YW50aWxlcyA8LSBjKDAuMSwgMC41LCAwLjkpICAjIFBlcmNlbnRpbGVzIDEwLCA1MCB5IDkwCm1vZGVscyA8LSBsYXBwbHkocXVhbnRpbGVzLCBmdW5jdGlvbihxKSBycSh5IH4gWCwgdGF1ID0gcSwgZGF0YSA9IGRmKSkgCiMgcSByZXByZXNlbnRhIGNhZGEgdW5vIGRlIGxvcyBwZXJjZXRpbGVzIAojdGF1IGNvbnRyb2xhIHF1w6kgcGFydGUgZGUgbGEgZGlzdHJpYnVjacOzbiBjb25kaWNpb25hbCBlc3RhbW9zIG1vZGVsYW5kby4KYGBgCgpgYGB7cn0Kc3VtbWFyeShxdWFudGlsZXMpCmBgYAoKCiMjIDxzcGFuIHN0eWxlPSAiQ29sb3I6IHZpb2xldDsiPiBBanVzdGFyIHVuIG1vZGVsbyBkZSBSZWdyZXNpw7NuIExpbmVhbCBlc3TDoW5kYXIgcGFyYSBjb21wYXJhY2nDs248L3NwYW4+CgpgYGB7cn0KbG1fbW9kZWwgPC0gbG0oeSB+IFgsIGRhdGEgPSBkZikKYGBgCgojIyA8c3BhbiBzdHlsZT0gIkNvbG9yOiB2aW9sZXQ7Ij4gQ3JlYXIgdW4gZGF0YWZyYW1lIHBhcmEgYWxtYWNlbmFyIHByZWRpY2Npb25lczwvc3Bhbj4KCmBgYHtyfQojIENyZWFtb3MgdW4gZGF0YSBmcmFtZSBjb24gdW5hIHNlY3VlbmNpYSBkZSB2YWxvcmVzIGRlIFggcXVlIHZhbiBkZXNkZSBlbCBtw61uaW1vIGhhc3RhIGVsIG3DoXhpbW8gZW4gZGYkWApYX3NlcSA8LSBkYXRhLmZyYW1lKFggPSBzZXEobWluKGRmJFgpLCBtYXgoZGYkWCksIGxlbmd0aC5vdXQgPSAxMDApKQojIENyZWFyIHVuIG51ZXZvIGRhdGEgZnJhbWUgcGFyYSBhbG1hY2VuYXIgbGFzIHByZWRpY2Npb25lcyBkZWwgbW9kZWxvIGRlIHJlZ3Jlc2nDs24KcHJlZF9kZiA8LSBkYXRhLmZyYW1lKAogIFggPSBYX3NlcSRYLAogIE9MUyA9IHByZWRpY3QobG1fbW9kZWwsIG5ld2RhdGEgPSBYX3NlcSkKKQpgYGAKCiMjIDxzcGFuIHN0eWxlPSAiQ29sb3I6IHZpb2xldDsiPiBBZ3JlZ2FyIHByZWRpY2Npb25lcyBkZSByZWdyZXNpw7NuIGN1YW50w61saWNhPC9zcGFuPgoKYGBge3J9CiNsb29wIHF1ZSByZWNvcnJlIHRvZG9zIGxvcyBjdWFudGlsZXMgZGVmaW5pZG9zIGVuIGxhIHZhcmlhYmxlICdxdWFudGlsZXMnCmZvciAoaSBpbiAxOmxlbmd0aChxdWFudGlsZXMpKSB7CiAgcHJlZF9kZltbcGFzdGUwKCJRIiwgcXVhbnRpbGVzW2ldICogMTAwKV1dIDwtIHByZWRpY3QobW9kZWxzW1tpXV0sIG5ld2RhdGEgPSBYX3NlcSkKfQpgYGAKCiMjIDxzcGFuIHN0eWxlPSAiQ29sb3I6IHZpb2xldDsiPiBHcmFmaWNhciByZXN1bHRhZG9zPC9zcGFuPgpgYGB7cn0KcGxvdCA8LSBnZ3Bsb3QoZGF0YSA9IGRmLCBhZXMoeCA9IFgsIHkgPSB5KSkgKwogIGdlb21fcG9pbnQoYWxwaGEgPSAwLjUpICsgICMgUHVudG9zIGRlIGRhdG9zIHJlYWxlcwogIGdlb21fbGluZShkYXRhID0gcHJlZF9kZiwgYWVzKHggPSBYLCB5ID0gT0xTLCBjb2xvciA9ICJPTFMiKSwgbGluZXR5cGUgPSAiZGFzaGVkIikgKwogIGdlb21fbGluZShkYXRhID0gcHJlZF9kZiwgYWVzKHggPSBYLCB5ID0gUTEwLCBjb2xvciA9ICJRdWFudGlsZSAxMCIpKSArCiAgZ2VvbV9saW5lKGRhdGEgPSBwcmVkX2RmLCBhZXMoeCA9IFgsIHkgPSBRNTAsIGNvbG9yID0gIlF1YW50aWxlIDUwIikpICsKICBnZW9tX2xpbmUoZGF0YSA9IHByZWRfZGYsIGFlcyh4ID0gWCwgeSA9IFE5MCwgY29sb3IgPSAiUXVhbnRpbGUgOTAiKSkgKwogIHNjYWxlX2NvbG9yX21hbnVhbCh2YWx1ZXMgPSBjKCJibGFjayIsICJibHVlIiwgInJlZCIsICJncmVlbiIpKSArCiAgbGFicyh0aXRsZSA9ICJDb21wYXJhY2nDs24gZGUgUmVncmVzacOzbiBDdWFudMOtbGljYSB5IExpbmVhbCIsCiAgICAgICB4ID0gIlBlc28gZGVsIEF1dG8gKHd0KSIsCiAgICAgICB5ID0gIk1pbGxhcyBwb3IgR2Fsw7NuIChtcGcpIiwKICAgICAgIGNvbG9yID0gIk1vZGVsbyIpICsKICB0aGVtZV9taW5pbWFsKCkKcHJpbnQocGxvdCkKYGBgCgojIDxzcGFuIHN0eWxlPSAiQ29sb3I6IHB1cnBsZTsiPkV4cGxpY2FjacOzbjwvc3Bhbj4KLSBMYSBsw61uZWEgbmVncmEgZGlzY29udGludWEgcmVwcmVzZW50YSBsYSByZWdyZXNpw7NuIGxpbmVhbCBlc3TDoW5kYXIgKE9MUykuCi0gTGFzIGzDrW5lYXMgYXp1bCwgcm9qYSB5IHZlcmRlIHJlcHJlc2VudGFuIGxhcyByZWdyZXNpb25lcyBjdWFudMOtbGljYXMgcGFyYSBsb3MgcGVyY2VudGlsZXMgMTAsIDUwIHkgOTAuCiAqTMOtbmVhIGF6dWwgKFF1YW50aWxlIDEwKTogTXVlc3RyYSBjw7NtbyBsb3MgYXV0b3MgY29uIG1lbm9yIGNvbnN1bW8gZGUgZ2Fzb2xpbmEgKHBlcmNlbnRpbCAxMCkgZXN0w6FuIGFmZWN0YWRvcyBwb3IgZWwgcGVzby4KIAogICpMw61uZWEgcm9qYSAoUXVhbnRpbGUgNTAgLSBNZWRpYW5hKTogUmVwcmVzZW50YSBsYSByZWxhY2nDs24gbWVkaWFuYSBlbnRyZSB3dCB5IG1wZywgZXF1aXZhbGVudGUgYSBsYSByZWdyZXNpw7NuIGN1YW50w61saWNhIGVuIGVsIHBlcmNlbnRpbCA1MC4KICAKICAqTMOtbmVhIHZlcmRlIChRdWFudGlsZSA5MCk6IE1vZGVsYSBsYSByZWxhY2nDs24gcGFyYSBsb3MgYXV0b3MgY29uIG1lam9yIGNvbnN1bW8gZGUgZ2Fzb2xpbmEgKHBlcmNlbnRpbCA5MCkuCgotT0xTIHN1YmVzdGltYSBvIHNvYnJlZXN0aW1hIGVuIGNpZXJ0YXMgcmVnaW9uZXMsIHlhIHF1ZSBzb2xvIG1vZGVsYSBsYSBtZWRpYSBkZSBtcGcsIG1pZW50cmFzIHF1ZSBRdWFudGlsZSBSZWdyZXNzaW9uIHBlcm1pdGUgZW50ZW5kZXIgY8OzbW8gY2FtYmlhIG1wZyBlbiBkaWZlcmVudGVzIG5pdmVsZXMuCgojIDxzcGFuIHN0eWxlPSAiQ29sb3I6IHB1cnBsZTsiPlJlZmVyZW5jaWFzPC9zcGFuPgotIE5naWVuZyBLaWFueWV3LCAqVW5kZXJzdGFuZGluZyBIb3cgUXVhbnRpbGUgUmVncmVzc2lvbiBXb3JrcyosIE1lZGl1bSAoMjAyMyku