Cómo extraer información del clasificador scikits.learn para luego usarla en código C

He entrenado a un grupo de SVM de RBF con scikits.learn en Python y luego seleccioné los resultados. Estas son para tareas de procesamiento de imágenes y una cosa que quiero hacer para la prueba es ejecutar cada clasificador en cada píxel de algunas imágenes de prueba. Es decir, extraiga el vector de características de una ventana centrada en el píxel (i, j), ejecute cada clasificador en ese vector de características, y luego continúe con el siguiente píxel y repita. Esto es demasiado lento para hacer con Python.

Aclaración: cuando digo “esto es demasiado lento …” quiero decir que incluso el código bajo el capó de Libsvm que usa scikits.learn es demasiado lento. De hecho, estoy escribiendo una función de decisión manual para la GPU, por lo que la clasificación en cada píxel ocurre en paralelo.

¿Es posible para mí cargar los clasificadores con Pickle, y luego capturar algún tipo de atributo que describa cómo se calcula la decisión a partir del vector de características, y luego pasar esa información a mi propio código C? En el caso de SVM lineales, simplemente podría extraer el vector de ponderación y el vector de polarización y agregarlos como entradas a una función de C. Pero, ¿qué es lo equivalente a hacer para los clasificadores RBF y cómo obtengo esa información del objeto scikits.learn?

Agregado: Primeros bashs de solución.

Parece que el objeto clasificador tiene el atributo support_vectors_ que contiene los vectores de soporte como cada fila de una matriz. También está el atributo dual_coef_ que es una matriz de coeficientes de 1 por len(support_vectors_) . De los tutoriales estándar sobre SVM no lineales, parece que uno debe hacer lo siguiente:

  • Calcule el vector de características v desde su punto de datos bajo prueba. Este será un vector que tiene la misma longitud que las filas de support_vectors_ .
  • Para cada fila i en support_vectors_ , calcule la distancia euclidiana cuadrada d[i] entre ese vector de soporte y v .
  • Calcule t[i] como gamma * exp{-d[i]} donde gamma es el parámetro RBF.
  • Suma dual_coef_[i] * t[i] sobre todo i . Agregue el valor del atributo intercept_ del clasificador scikits.learn a esta sum.
  • Si la sum es positiva, clasifica como 1. De lo contrario, clasifica como 0.

Agregado: En la página 9 numerada de este enlace de documentación, se menciona que, de hecho, el atributo intercept_ del clasificador contiene el término de sesgo. He actualizado los pasos anteriores para reflejar esto.

Sí, su solución se ve bien. Para pasar la memoria en bruto de una matriz numpy directamente a un progtwig en C, puede usar los ayudantes ctypes de numpy o envolver su progtwig C con cython y llamarla directamente pasando la matriz numpy (consulte el documento en http://cython.org para más detalles).

Sin embargo, no estoy seguro de que intentar acelerar la predicción en una GPU sea el enfoque más sencillo: se sabe que las máquinas de vectores de soporte del kernel son lentas en el tiempo de predicción, ya que su complejidad depende directamente de la cantidad de vectores de soporte que pueden ser altos – Problemas lineales (multimodales).

Los enfoques alternativos que son más rápidos en el tiempo de predicción incluyen redes neuronales (probablemente más complicadas o más lentas de entrenar que las SVM que solo tienen 2 hiper-parámetros C y gamma) o transformar sus datos con una transformación no lineal basada en distancias a prototipos + umbrales Agrupación máxima sobre áreas de imagen (solo para la clasificación de imágenes).

  • Para el primer método encontrará buena documentación sobre el tutorial de aprendizaje profundo.

  • Para el segundo, lea los artículos recientes de Adam Coates y eche un vistazo a esta página sobre la extracción de características de kmeans.

Finalmente, también puede intentar usar modelos NuSVC cuyo parámetro de regularización nu tenga un impacto directo en el número de vectores de soporte en el modelo ajustado: menos vectores de soporte significan tiempos de predicción más rápidos (aunque verifique la precisión, será una compensación entre predicciones) Velocidad y precisión al final).