Ir al contenido
σestadistica.ar

Script

No paramétricas

Las pruebas que no suponen normalidad, y el bootstrap para ponerle un intervalo a lo que no tiene fórmula. Con el azar escrito a mano, para que R y Python sorteen las mismas filas.

Descargar

Proyecto en R y Python · ZIP · 139 KB

En R alcanza con lo que ya trae; en Python hace falta SciPy.

Tirar el apareamiento cuesta el resultado

La base de ejemplo tiene 148 personas evaluadas dos veces: al entrar y al salir. Las cuatro pruebas, sobre exactamente las mismas dos columnas:

Prueba¿Usa el apareamiento?pQué concluye
Wilcoxon de rangos con signoSí0,0004Hay efecto
Prueba de los signosSí0,0002Hay efecto
Mann-WhitneyNo0,206No hay efecto
t de WelchNo0,220No hay efecto

La misma tabla, la conclusión al revés. Y la razón es aritmética, no doctrinaria: el cambio típico es de 1,7 puntos con un desvío de 5,7, mientras que lo que separa a una persona de otra son 12,5 puntos al entrar y 10,6 al salir.

La comparación apareada mide el efecto contra la variabilidad de los cambios. La otra tiene que buscarlo adentro de la variabilidad entre personas, que es casi el doble de grande, y ahí se pierde. El apareamiento es información que está en los datos, y tirarla no es una decisión conservadora: es perder el resultado.

Pasa más de lo que parece. Cada vez que alguien pega la columna del antes debajo de la del después y corre una prueba de dos muestras, está haciendo exactamente esto.

Mann-Whitney no compara medianas

Es la afirmación más repetida sobre esta prueba y es falsa. Lo que contrasta es P(X > Y) = ½: la probabilidad de que un caso tomado al azar de un grupo supere a uno del otro. Solo cuando las dos distribuciones tienen la misma forma esa hipótesis equivale a la de medianas iguales.

Por eso el descargable escribe P(X > Y) = 0,301 al lado del valor p, y el desplazamiento de Hodges-Lehmann, que es la mediana de todas las diferencias entre un caso de un grupo y uno del otro. Ese último es el número que corresponde informar como «de cuánto es la diferencia».

Un promedio y una mediana que apuntan al revés

El gasto en materiales del ejemplo trae tres valores enormes —los mismos que el descargable de gráficos deja a la vista en su diagrama de caja—, y los tres cayeron del lado de Control:

diferencia de medianas    +11.626    IC 95 % [5.170; 16.454]
diferencia de medias       −4.693    IC 95 % [−25.151; 12.034]

Signos opuestos. Y las pruebas dicen lo mismo: Mann-Whitney da p = 0,00003 y la t de Welch p = 0,625. La t no ve nada porque los tres casos le inflaron la varianza; la de rangos no los ve como valores enormes, los ve como tres puestos más arriba en el orden.

Con datos asimétricos la prueba de rangos suele tener más potencia que la paramétrica, que es lo contrario de lo que se suele creer.

Tres intervalos de bootstrap, no uno

Una prueba de rangos dice si hay diferencia; no dice de cuánto, y para casi cualquier estadístico que no sea una media no hay fórmula cerrada que dé un intervalo. El bootstrap la reemplaza por fuerza bruta: en el ejemplo, 2000 remuestreos de la propia muestra. Los tres intervalos que salen no dan lo mismo:

Sobre el gastoValorPercentilBCa
Mediana35.818[31.992; 39.030][31.992; 39.030]
Media44.480[36.723; 54.956][37.783; 58.968]
Rango intercuartílico20.763[16.809; 23.802][17.569; 25.289]
Desvío estándar58.333[14.179; 86.444][30.825; 99.443]

Para la mediana los dos coinciden. Para el desvío, el límite inferior del percentil es 14.179 y el del BCa es 30.825: más del doble. El percentil es el que casi todo el mundo informa y el único de los tres que no corrige nada; el BCa corrige el sesgo y la asimetría, con dos constantes que salen de las propias réplicas y de un jackknife. El descargable avisa cuando el corrimiento pasa del 10 % del ancho.

Por qué el azar está escrito a mano

Porque sample() de R y random de Python no sortean lo mismo. Los dos usan Mersenne Twister, pero siembran el estado distinto y convierten el número de 32 bits en un índice distinto. Con la misma semilla y el mismo n, la primera fila remuestreada ya sale diferente.

En un bootstrap eso no es un detalle de formato: cada límite de cada intervalo sale de qué filas tocaron. El proyecto implementa el generador de Lehmer de Park y Miller —x ← 48271·x mod 2³¹−1— porque el producto más grande entra exacto en un número de doble precisión, que es lo único que R tiene. El barajado de la permutación es un Fisher-Yates escrito también a mano, por lo mismo.

Y apareció una segunda: las réplicas se ordenan para sacar los cuantiles, así que hay que redondearlas antes o dos que difieren en el último bit intercambian su lugar. Pero round() de Python y round() de R no desempatan igual: sobre el mismo número, round(54955.843065, 5) da 54955,84307 en uno y 54955,84306 en el otro. Con dos mil réplicas y un cuantil interpolado, caer justo en la mitad deja de ser raro —al ejemplo le pasó—, así que el redondeo también está escrito a mano.

Qué deja

ArchivoQué trae
apareadas.csvWilcoxon y los signos, y las dos pruebas que no corresponden
el-cambio.csvLa mediana, la media y el desvío del cambio, y si el apareamiento decide
mann-whitney.csvU, el p, P(X > Y), el Hodges-Lehmann y la t de Welch al lado
kruskal-wallis.csvH con corrección por empates, ε² y los grados de libertad
kruskal-grupos.csvn, mediana y rango promedio de cada grupo
bootstrap.csvPercentil, básico y BCa para cada estadístico, con z₀ y la aceleración
permutacion.csvLa prueba de permutación sobre la diferencia de medianas
avisos.csvCada supuesto que no se cumple y cada conclusión que depende de una decisión
no-parametricas.mdEl informe redactado

Qué se compara con qué se declara en datos/parametros.csv: el par antes/después, la respuesta y el grupo, el factor de tres o más niveles, cuántas réplicas y con qué semilla. Cualquiera de los bloques puede quedar vacío.

Lo que no hace

No hay Friedman ni ninguna prueba para más de dos medidas repetidas.

No hay post hoc después de Kruskal-Wallis. Las comparaciones de a pares con corrección están en el descargable de ANOVA.

No hay bootstrap para datos apareados ni para diseños con estratos. El remuestreo es simple, o por grupo en el caso de la diferencia.

No hay intervalos bootstrap-t. Requieren estimar el error estándar dentro de cada réplica, que multiplica el costo por el tamaño de la muestra.

Cómo está verificado

Es el primer descargable de la serie que depende del azar, y eso cambia qué significa verificarlo. El verificador reimplementa el generador número por número y comprueba las propiedades que tiene que cumplir: que el estado nunca llegue a cero, que no se repita en veinte mil pasos, que los índices se repartan parejo y que una permutación sea una permutación. Después reconstruye las mismas réplicas —se puede, porque el generador es reproducible— y rehace los tres intervalos y la prueba de permutación desde cero. Wilcoxon, los signos, Mann-Whitney y Kruskal-Wallis van contra scipy, y además contra src/lib/no-parametricas.ts, la calculadora del propio sitio, invocada desde Node. Comprueba también las identidades que no pueden fallar: que el intervalo básico sea el reflejo exacto del percentil, que el p de permutación nunca baje de 1/(réplicas+1) y que la recurrencia binomial de la prueba de los signos coincida con los coeficientes exactos. Prueba cinco bases más: solo apareadas con empates, tres grupos, una muestra con muchos valores repetidos, una con pocas réplicas y una con grupos de tamaños muy distintos —esta última se agregó porque sin ella el sabotaje que remuestrea el segundo grupo con el tamaño del primero pasaba sin detectarse—. Son 562 comprobaciones, los veintiún sabotajes se detectan, y R y Python escriben los diez archivos idénticos byte a byte.