library(lpSolve)
<- function(y){
mediana.lp # Calcula el valor t que minimiza sum_i |y_i-t|
<- length(y)
n <-c(rep(1,2*n), 0, 0)
cvec <- y
b <- rep(1, n)
unos <- cbind(diag(unos), diag(-unos), unos, -unos)
A <- rep('=', n)
dir
<- lp('min', cvec, A, dir, b)$solution
optimo return(optimo[2*n+1] - optimo[2*n+2])
}
# Ejemplos
<- c(2, 3, 4, 5, 6)
y mediana.lp(y)
#> [1] 4
set.seed(123)
<- rnorm(500)
y mediana.lp(y)
#> [1] 0.02045071
Se explica aquí cómo aprovechar que la mediana es, en cierto sentido, un valor extremo, para calcularla sin tener que ordenar los datos. También se comenta por qué esta observación tiene implicaciones relevantes en lo que se conoce como regresión de cuantiles.
La mediana resuelve un problema de programación lineal
Dice Aristóteles en la Ética a Nicómaco que “la virtud es un término medio, pero con respecto a lo mejor y al bien, es un extremo”, e igualmente en estadística las medidas de la posición central de un conjunto de datos se pueden considerar extremos, en el sentido de ser las que minimizan alguna medida de la magnitud de las desviaciones de los datos a una posición central dada. Por ejemplo, la mediana es el valor que minimiza la suma de desviaciones absolutas. Si definimos la función objetivo
entonces las medianas son los mínimos globales de
Desde este punto de vista, en lugar de ordenar los datos, el cálculo de la mediana requiere resolver un problema de optimización, que por un lado es fácil porque es convexo (no hay mínimos locales) pero por otra parte en la función objetivo hay un valor absoluto, lo que impide el uso de métodos que requieran derivadas.
La observación clave es que el problema de optimización que hay que resolver para calcular la mediana se puede escribir como un problema de programación lineal, por lo que basta usar cualquier método estándar para este tipo de problemas (por ejemplo, el famoso algoritmo del simplex).
Veamos cómo escribir el problema de forma apropiada:
Para
El valor de la mediana es el valor óptimo
En forma estándar
Recordemos que un problema de programación lineal en forma estándar es aquel en el que queremos encontrar el vector
En función de las nuevas variables
Obsérvese que
Cómo resolverlo con R
Hace unos años escribí una guía sobre cómo resolver problemas de optimización lineal con R en la que se explicaban las principales características del paquete lpSolve
. Aquí lo voy a usar para calcular la mediana. Para entender mejor la función hay que escribir nuestro problema en la forma (1). Para ello, definimos
Regresión de cuantiles
Este ejemplo lo usé como ejercicio de programación lineal cuando impartí la asignatura Investigación Operativa en la UAM, y puede parecer que es una forma muy rebuscada de calcular la mediana, pero su interés es mayor de lo que parece. El modelo de regresión de cuantiles lineal consiste en suponer que la mediana (u otros cuantiles) de la distribución de una variable respuesta
Por un razonamiento similar al que hemos descrito en esta entrada, el vector