¿Cómo puedo guardar de manera eficiente un marco de datos de python pandas en hdf5 y abrirlo como un marco de datos en R?

Creo que el título cubre el tema, pero para aclarar:

La Los pandas El paquete python tiene un tipo de datos DataFrame para almacenar datos de tablas en python. También tiene una interfaz conveniente para el hdf5 formato de archivo, por lo que Pandas DataFrames (y otros datos) se pueden guardar usando una interfaz simple similar a dict (suponiendo que tenga Pytables instalado)

import pandas 
import numpy
d = pandas.HDFStore('data.h5')
d['testdata'] = pandas.DataFrame({'N': numpy.random.randn(5)})
d.close()

Hasta aquí todo bien. Sin embargo, si luego trato de cargar ese mismo hdf5 en RI, veo que las cosas no son tan simples:

> library(hdf5)
> hdf5load('data.h5')
NULL
> testdata
$block0_values
         [,1]      [,2]      [,3]       [,4]      [,5]
[1,] 1.498147 0.8843877 -1.081656 0.08717049 -1.302641
attr(,"CLASS")
[1] "ARRAY"
attr(,"VERSION")
[1] "2.3"
attr(,"TITLE")
[1] ""
attr(,"FLAVOR")
[1] "numpy"

$block0_items
[1] "N"
attr(,"CLASS")
[1] "ARRAY"
attr(,"VERSION")
[1] "2.3"
attr(,"TITLE")
[1] ""
attr(,"FLAVOR")
[1] "numpy"
attr(,"kind")
[1] "string"
attr(,"name")
[1] "N."

$axis1
[1] 0 1 2 3 4
attr(,"CLASS")
[1] "ARRAY"
attr(,"VERSION")
[1] "2.3"
attr(,"TITLE")
[1] ""
attr(,"FLAVOR")
[1] "numpy"
attr(,"kind")
[1] "integer"
attr(,"name")
[1] "N."

$axis0
[1] "N"
attr(,"CLASS")
[1] "ARRAY"
attr(,"VERSION")
[1] "2.3"
attr(,"TITLE")
[1] ""
attr(,"FLAVOR")
[1] "numpy"
attr(,"kind")
[1] "string"
attr(,"name")
[1] "N."

attr(,"TITLE")
[1] ""
attr(,"CLASS")
[1] "GROUP"
attr(,"VERSION")
[1] "1.0"
attr(,"ndim")
[1] 2
attr(,"axis0_variety")
[1] "regular"
attr(,"axis1_variety")
[1] "regular"
attr(,"nblocks")
[1] 1
attr(,"block0_items_variety")
[1] "regular"
attr(,"pandas_type")
[1] "frame"

Lo que me lleva a mi pregunta: idealmente, podría guardar de R a pandas. Obviamente puedo escribir un envoltorio de pandas a R (creo... aunque creo que si uso un pandas índice múltiple eso podría volverse más complicado), pero no creo que pueda usar fácilmente esos datos en pandas. ¿Alguna sugerencia?

Bono: lo que yo democracia quiero hacer es usar el tabla de datos paquete en R con un marco de datos pandas (el enfoque de codificación es sospechosamente similar en ambos paquetes). Cualquier ayuda en eso muy apreciada.

preguntado el 05 de septiembre de 12 a las 10:09

¿Cuál es el problema exactamente? No testdata$block0_values devolver los valores que guardaste del panda? -

El problema es poder reabrir nuevamente en pandas (ver la última parte de mi pregunta). Puedo convertir a un R data.frame (o data.table) hacer algunas manipulaciones, pero luego no puedo volver a guardar en pandas fácilmente (sin otro contenedor, probablemente más complicado). -

Creo que lo que estás preguntando sería muy útil. Por ahora, sería aceptable usar algo como esto: pandas.pydata.org/pandas-docs/stable/r_interface.html o tal vez incluso usar el soporte de puente R en ipython reciente? (ipython.org/ipython-doc/stable/config/extensions/rmagic.html) -

5 Respuestas

Si todavía está mirando esto, eche un vistazo a esta publicación en los grupos de Google. Muestra cómo intercambiar datos entre pandas/R a través de HDF5.

https://groups.google.com/forum/?fromgroups#!topic/pydata/0LR72GN9p6w

Respondido el 18 de enero de 13 a las 20:01

Sorprendente, la primera vez que leí esto no pensé que iría a ninguna parte, pero me encontré con esto nuevamente y parece que se han hecho progresos, particularmente porque ahora está en los documentos: pandas.pydata.org/pandas-docs/stable/…. Probaré y te daré crédito si funciona;) - griffith rees

Lamentablemente, no pude hacer que funcionara, y la carga de hdf5 de R parece llevar mucho tiempo. Ahora estoy usando la nueva función fread en data.table: r.789695.n4.nabble.com/… - griffith rees

Tendría sentido bajar a pytables y almacenar/obtener sus datos allí.

En última instancia, un DataFrame es un dict de Series, que es lo que es una tabla HDF5. Existen limitaciones en la traducción debido a tipos de d incompatibles, pero para datos numéricos debería ser sencillo.

La forma en que los pandas almacenan su HDF5 se ve más como una mancha binaria. Tiene que soportar todos los matices de un DataFrame que HDF5 soporta limpiamente.

https://github.com/dalejung/trtools/blob/master/trtools/io/pytables.py

Tiene algo de ese tipo de código munging pandas/hdf5.

Respondido el 05 de Septiembre de 12 a las 19:09

Entonces, ¿recomienda escribir una capa de compatibilidad personalizada en pytables entre pandas y R? Supongo que necesito averiguar cuál tiene el formato HDF5 más simple (R o pandas) y convertirlo en mi tipo de datos básico, luego proporcionar un convertidor en cualquier extremo cada vez que lea o escriba. - griffith rees

Sí. Posiblemente podría escribir un adaptador R para leer/escribir pandas hdf semánticamente. Pero parece más fácil crear un HDF semántico y tener envoltorios simples en ambos extremos. - dale jung

Recomiendo el uso de pluma, construido por Wes y Hadley para resolver el problema de la transferencia de datos entre R y Python de manera eficiente.

Python

import numpy as np
import pandas as pd
import feather as ft

df = pd.DataFrame({'N': np.random.randn(5)})
ft.write_dataframe(df, 'df.feather')

R

library(data.table)
library(feather)

dt <- data.table(read_feather("df.feather"))
dt
           N
1: 0.2777700
2: 1.4083377
3: 1.2940691
4: 0.8221348
5: 1.8552908

Respondido el 30 de Septiembre de 16 a las 16:09

¡Buena sugerencia! No es hdf5, pero podría decirse que resuelve el flujo de trabajo básico que quería. Hmmm... necesito decidir si aceptar esta respuesta, ya que no responde directamente a la pregunta planteada, pero sugiere más profundamente una forma de arreglar el flujo de trabajo general que esperaba. - griffith rees

Cómo escribir un marco de datos en HDF5 para que pueda leerse en R ahora se encuentra en la documentación de Pandas: http://pandas-docs.github.io/pandas-docs-travis/io.html#external-compatibility

Respondido 01 Oct 18, 13:10

Sí, ya he vinculado allí en mi comentario sobre la primera respuesta. Lamentablemente, no es una biblioteca muy eficiente en mis propias pruebas personales (en comparación con el fread de data.table), pero tal vez debería darle otra oportunidad. Gracias por el interés. - griffith rees

Podrías usar csv archivos como el formato de datos común. Tanto R como python pandas pueden trabajar fácilmente con eso. Es posible que pierda algo de precisión, pero si esto es un problema depende de su problema específico.

Respondido el 05 de Septiembre de 12 a las 10:09

Sí, por supuesto, pero eso significaría que perdería la velocidad y la comodidad del formato hdf5. R es muy lento para analizar archivos de texto grandes (es por eso que a menudo uso el formato dta de STATA para grandes datos en R). Prefiero no escribir código para escribir en dta en python (hay un lector disponible en el paquete statsmodels). - griffith rees

Irónicamente, eso es lo que hago ahora debido a la función fread súper rápida de data.table para csv. Perdón por el voto negativo anterior. - griffith rees

@GriffithRees Podría marcar mi respuesta como la correcta para expiar el voto negativo;) - Pablo Hiemstra

@Paul Pero, tu respuesta no es la correcta. CSV simplemente no es una solución práctica, ni arquitectónicamente buena, ni creativa. - Testamento

@GriffithRees, parece que todavía no hay progreso y me han molestado con este problema para siempre. Empecé a trabajar en mi propio formato de datos binarios dedicado para marcos de datos que es compatible con R, Python's Pandas, C#/F#'s Deedle y Scala's Saddle. Publicaré un enlace si alguna vez termino mi proyecto. - uday

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.