Sobre la peculiarísima implementación del modelo lineal en (pseudo-)scikit-learn

Si ejecutas import numpy as np from sklearn.linear_model import LinearRegression n = 1000 X = np.random.rand(n, 2) Y = np.dot(X, np.array([1, 2])) + 1 + np.random.randn(n) / 2 reg = LinearRegression().fit(X, Y) reg.intercept_ reg.coef_ se obtiene más o menos lo esperado. Pero si añades una columna linealmente dependiente, X = np.column_stack((X, 1 * X[:,1])) ocurren cosas de la más calamitosa especie: Y = np.dot(X, np.array([1, 2, 1])) + 1 + np.random.randn(n) / 2 reg = LinearRegression().fit(X, Y) reg.coef_ # array([ 9.89633991e-01, -1.63740303e+14, 1.63740303e+14]) Comentarios: Diríase que la implementación del modelo lineal en scikit-learn no es la que se estudia por doquier (la prima, la inversa, etc.); sospecho que convierte el error cuadrático en una función que depende de los coeficientes y se la pasan a un optimizador (más o menos) genérico. Supongo que la implementación actual pasa todas las pruebas unitarias. Y sospecho, además, que las pruebas unitarias no las ha planteado un estadístico. Así que tal vez los de scikit-learn no saben que tienen problemas de colinealidad; y si alguien se lo ha comentado, igual no han comprendido el issue. Para la predicción, el problema arriba apuntado no es tal. Aun con coeficientes desaforados y siempre que no haya problemas de precisión numérica, tanto da hacer las cosas como todo el mundo o implementando ocurrencias como la anterior. Pero para todo lo demás (p.e., impacto de variables, etc.), la implementación es de traca y no vale para maldita de Dios la cosa. Aunque a estas alturas de siglo, ¿quién en su sano juicio usa el modelo lineal básico? Además, en la práctica, no hay problemas de colinealidad (ni aproximada ni, mucho menos, exacta). Hummm… ¿O sí? Mi colega Cañadas ha escrito una entrada en su blog sobre la codificación de variables categóricas donde denuncia cómo en Python las funciones más habituales crean columnas linealmente dependientes por defecto (por no omitir el primer nivel). O sea, en Python, si no andas con cuidado, acabas con la suela llena de kk de perro.

17 de julio de 2019 · Carlos J. Gil Bellosta

Mi infraestructura para Python

Resumen: He decidido usar RStudio como IDE para Python. RStudio no es el mejor IDE para desarrollar, pero es incomparablemente mejor que cualquier otro IDE para explorar, etc. Funciona muy bien y solo puede mejorar. He decidido pasar de Jupyter. Los notebooks valen para lo que valen, pero no para lo que hago. En caso de necesidad, uso Rmarkdown con bloques de Python. De nuevo, funcionan muy bien y solo pueden mejorar. Finalmente, he decidido pasar de Anaconda. Tiene incompatibilidades con RStudio. Particularmente, cuando los módulos de Python tratan de cargar shared libraries. Los módulos de Anaconda tienen el vicio de buscarlos dentro del directorio de instalación, pero al lanzar el intérprete de Python a través de reticulate, en Linux parece que los busca en el sistema (por debajo de /usr/lib y similares). Y todo se rompe mucho. Mucho y muy, muy feo. Así que uso los Python (3.7 cuando puedo, otras versiones cuando me obligan) del sistema. Pero la instalación del sistema es mínima. He creado varios environments ad hoc (y dentro de un directorio ad hoc para ellos) y obligo a reticulate a usarlos (vía use_virtualenv()) según conveniencia. En ellos tengo todas las dependencias (de numpy para arriba). ...

6 de junio de 2019 · Carlos J. Gil Bellosta

Sr. Python, muchas gracias por su candidatura; ya le llamaremos cuando... tenga modelos mixtos

Era casi todavía el siglo XX cuando yo, desesperado por hacer cosas que consideraba normales y que SAS no me permitía, pregunté a un profesor por algo como C pero para estadística. Y el profesor me contó que conocía a alguien que conocía a alguien que conocía a alguien que usaba una cosa nueva que se llamaba R y que podía servirme. Fue amor a primera vista, pero esa es otra historia. La relevante aquí es que volví a hablar con aquel profesor para agradecerle el consejo y, de paso, le pregunté que por qué no lo usaba él. Me contestó que porque en R no había modelos mixtos (aunque nlme es anterior, del 99; ¡a saber en qué estado se encontraba entonces!). ...

12 de febrero de 2019 · Carlos J. Gil Bellosta

Extingámonos con dignidad: generaciones actuales y futuras, no incurramos en los errores de las anteriores

Participé el otro día en una cena con gente friqui. Constaté con cierto desasosiego cómo han virado los sujetos pasivos de nuestra indignación profesional a lo largo de los años. Antaño, fueron los viejos que seguían apegados a la paleoinformática. Hogaño, los primíparos que usan Python y desdeñan R. Tengo sentimientos encontrados y no sé qué más añadir.

8 de octubre de 2018 · Carlos J. Gil Bellosta

Un generador de datos sintéticos para proteger la privacidad de los microdatados

DataSynthesizer (véase también el correspondiente artículo) es un programa en Python que: Toma una tabla de datos (microdatos, de hecho) que contiene información confidencial. Genera otra aleatoria pero que conserva (¿los conservará?) la estructura básica de la información subyacente (conteos, correlaciones, etc.). Está pensado para poder realizar el análisis estadístico de (determinados) datos sin verlos propiamente. Particularmente interesante es el algoritmo para preservar la correlación entre columnas. [Nota: he aprovechado la entrada para acuñar el neologismo microdatado para referirme a quien figura en un fichero de microdatos.] ...

23 de mayo de 2018 · Carlos J. Gil Bellosta

Una comparación de lenguajes de programación en una esquinita pequeña de la economía

El título, no el de esta entrada sino el de A Comparison of Programming Languages in Economics, es una sinécdoque confusa. Que nadie busque en él consejo sobre qué lenguaje estudiar si le interesa el mundo de la economía (en general). O fuera de ella (también en general). Encontrará más bien la implementación de la solución a un único problema dentro de los muchos que supongo comprende esa disciplina. Uno, además, con el que no he visto (en persona) a economista alguno ganarse el pan ni en la academia ni fuera de ella. ...

6 de octubre de 2017 · Carlos J. Gil Bellosta

Python y R: una perspectiva markoviana

Hoy he visto aquí y he escrito m <- matrix(c(74, 15, 10, 1, 11, 50, 38, 1, 5, 4, 90, 1, 17, 4, 19, 60), 4, 4, byrow = TRUE) m <- m / 100 luego m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m%*% m%*% m%*% m%*% m%*% m%*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m %*% m%*% m%*% m%*% m%*% m%*% m%*% m # [,1] [,2] [,3] [,4] #[1,] 0.1926676 0.1133218 0.6696203 0.02439024 #[2,] 0.1926647 0.1133206 0.6696245 0.02439024 #[3,] 0.1926638 0.1133202 0.6696258 0.02439024 #[4,] 0.1926675 0.1133218 0.6696205 0.02439025 y finalmente res <- eigen(t(m)) res$vectors[,1] / sum(res$vectors[,1]) #[1] 0.19266473 0.11332059 0.66962444 0.02439024 Aquí dice por qué.

6 de septiembre de 2017 · Carlos J. Gil Bellosta

Un curso de 15 horas de introducción a la programación

Hoy comienzo a enseñar un curso de introducción a la programación para recién graduados que comenzarán un máster de matemáticas aplicadas con incursiones en la llamada ciencia de datos. Serán 4 sesiones con el siguiente contenido: Sesión 1, programación imperativa: variables, condicionales y bucles. Sesión 2, programación orientada a objetos. Sesión 3, colecciones: listas, tuplas, conjuntos, diccionarios, etc. Sesión 4, programación funcional: map, reduce, fold, foldLeft, scan, filter, etc. Los lenguajes a utilizar serán R y Python (via Jupyter). No me he atrevido a añadir Scala (como ejemplo de cómo deben hacerse las cosas, además de ser un lenguaje, para variar, tipado y no interpretado) por falta de tiempo. ...

19 de septiembre de 2016 · Carlos J. Gil Bellosta

Rmd2R: un conversor de lo que su propio nombre indica

Mis clases de/con R suelen consistir en un guión que es un programa en R con muchos comentarios y ejercicios. Con el tiempo, estos últimos tienden a crecer hasta el punto de que se convierte casi en un fichero de texto comentado con aspersión —en su acepción no-DRAE de efecto— de líneas de código. Mejor, me he dicho recientemente, usar Rmarkdown. Pero Rmarkdown sirve para lo que sirve: como fuente para compilar ficheros pensados para ser leídos por seres humanos. Contiene demasiada información irrelevante —formato, etc.— para un guión. ...

25 de mayo de 2016 · Carlos J. Gil Bellosta

rPython + feather

Supongo que a estas alturas todos conoceréis feather y rPython. Hoy los vais a ver trabajar juntos. Primero solo en R: library(feather) path <- "/tmp/my_data.feather" write_feather(cars, path) my_cars <- read_feather(path) Ahora, para pasarle datos a Python: library(rPython) python.exec("import feather") python.exec("a = feather.read_dataframe('/tmp/my_data.feather')") python.exec("print a") Y, finalmente, para crear datos grandes en Python y devolvérselos a R: python.exec("import numpy as np") python.exec("import pandas as pd") python.exec("arr = np.random.randn(10000000)") python.exec("arr[::10] = np.nan") python.exec("df = pd.DataFrame({'column_{0}'.format(i): arr for i in range(10)})") python.exec("feather.write_dataframe(df, '/tmp/test.feather')") python.data <- read_feather("/tmp/test.feather") dim(python.data) #[1] 10000000 10 Los tiempos, que los mida cada cual.

6 de abril de 2016 · Carlos J. Gil Bellosta