2012-07-29 17 views
12

¿Cómo uso scikit-learn para entrenar un modelo en un gran csv de datos (~ 75MB) sin tener problemas de memoria?Scikit y Pandas: Ajuste de datos grandes

Estoy usando el cuaderno de IPython como entorno de programación, y pandas + sklearn paquetes para analizar los datos del tutorial del reconocedor de dígitos de kaggle.

Los datos están disponibles en la webpage, enlace a my code, y aquí está la error message:

KNeighborsClassifier se utiliza para la predicción.

Problema:

"MemoryError" se produce al cargar gran conjunto de datos usando read_csv función . Para evitar temporalmente este problema, debo reiniciar el núcleo , que luego la función read_csv carga con éxito el archivo, pero se produce el mismo error cuando vuelvo a ejecutar la misma celda.

Cuando la función read_csv carga el archivo con éxito, después de hacer cambios a la dataframe, que pueden pasar las características y etiquetas para la función() ajuste del KNeighborsClassifier. En este punto, se produce un error de memoria similar.

He intentado lo siguiente:

Iterar a través del archivo CSV en trozos, y ajustar los datos en consecuencia, pero el problema es que el modelo predictivo se sobrescribe cada vez que un fragmento de datos.

¿Qué crees que puedo hacer para entrenar con éxito mi modelo sin tener que tener problemas de memoria?

+0

Su código + datos funciona muy bien en mi portátil. Requiere aproximadamente 1.2 GB de memoria. ¿Cuánta memoria tiene tu sistema? – Sicco

+1

Lo tengo trabajando usando loadtxt. Incluso sin que se produzca el error de memoria, ejecutar solo ~ 75 mb de datos en el algoritmo consume más de 1 GB de RAM ... No estoy seguro de si estoy haciendo algo mal en mi código. (http://pastie.org/4354911) (cuaderno ipython). Si solo es el algoritmo el que toma tanto tiempo, ¿cómo se cargan gigabytes de datos en el algoritmo sin tomar tanto tiempo para crear un modelo? –

+4

Puede usar un algoritmo que se pueda entrenar de forma incremental, procesando solo partes (pequeñas) de los datos a la vez. Un estimador en scikit-learn es capaz de hacer esto si implementa el método 'partial_fit'. – Sicco

Respuesta

10

Nota: al cargar los datos con los pandas se creará un objeto DataFrame donde cada columna tiene un tipo de datos homogénea para todas las filas 2 columnas, pero puede tener tipos de datos distintos (por ejemplo, enteros, fechas, cuerdas).

Cuando se pasa una instancia DataFrame a un modelo scikit-learn va a asignar primero una matriz 2D numpy homogénea con dtype np.float32 o np.float64 (dependiendo de la implementación de los modelos). En este punto, tendrá 2 copias de su conjunto de datos en la memoria.

Para evitar esto, puede escribir/reutilizar un analizador CSV que asigna directamente los datos en el formato interno/tipo esperado por el modelo scikit-learn. Puede probar numpy.loadtxt por ejemplo (eche un vistazo a la docstring para ver los parámetros).

Además, si sus datos son muy escasos (muchos valores cero), será mejor utilizar una estructura de datos scipy.sparse y un modelo scikit-learn que pueda tratar con un formato de entrada de este tipo (consulte las instrucciones para saber). Sin embargo, el formato CSV en sí mismo no es muy adecuado para datos escasos y no estoy seguro de que exista un analizador CSV-to-scipy.sparse directo.

Editar: para referencia KNearestNeighborsClassifer asignar gama distancias temporal con forma (n_samples_predict, n_samples_train) que es un gran desperdicio cuando se necesita solamente (n_samples_predict, n_neighbors) lugar.Este problema se puede seguir aquí:

https://github.com/scikit-learn/scikit-learn/issues/325

+0

¡loadtxt funciona de maravilla! –

+0

El modelo scikit-learn tampoco causa ninguna excepción de memoria. El único problema ahora es ... dado que los datos son tan grandes, el algoritmo tarda mucho tiempo en crear un modelo. Ojalá hubiera una manera de hacer esto mucho más rápido ... –

+2

Deberías tratar de usar 'KNeighborsClassifier' en modo fuerza bruta (en lugar de balltree) pero luego los tiempos de predicción pueden ser demasiado lentos. Alternativamente, puede utilizar modelos simples como 'sklearn.linear_model.Perceptron',' sklearn.naive_bayes.MultinomialNB' o 'sklearn.neighbors.NearestCentroidClassifier'. Finalmente, también puede intentar entrenar un modelo en una submuestra pequeña de sus datos para obtener una primera idea rápida de la precisión predictiva y luego duplicar el tamaño del conjunto de datos e iterar. – ogrisel