2012-07-18 8 views
5

Me han sugerido csv-conduit como un buen paquete Haskell para trabajar con archivos CSV. Quiero aprender cómo funciona, pero la documentación es demasiado escueta para un programador Haskell novato.Haskell csv-conducto en GHCi

¿Hay alguna manera de averiguar cómo funciona por ensayo y error en GHCi?

Más concretamente, debo cargar los módulos y archivos de GHCi o debería escribir un archivo SA sencilla para cargarlos y luego se mueven alrededor interactiva?


I-csv mencionado conducto, pero estoy abierto a cualquier uso de paquete CSV. Solo necesito poner las manos en una y jugar con ella, hasta que me sienta a gusto (al igual que haría en IDLE).

Respuesta

2

Ha intentado Text.CSV? Puede ser más apropiado si recién estás comenzando con Haskell, ya que es mucho más simple. En cuanto a explorar nuevos módulos, solo puede cargarlo en GHCi, no es necesario escribir un archivo adicional.

5

Tome un vistazo a la siguiente función: readCSVFile :: :: (MonadResource m, CSV ByteString a) => CSVSettings -> FilePath -> m [a]

Su relativamente fácil de llamar, ya que sólo hay un CSVSettings, como defCSVSettings, y una FilePath (también conocido como String), "file.csv" o algo así.

Por lo tanto, después de la llamada, se obtiene (MonadResource m, CSV ByteString a). Podemos resolver esto a la vez para descubrir un tipo apropiado para esto. Estamos realizando IO en esta operación, por lo que para MonadResource m, m debe ser ResourceT IO, que es una instancia de MonadBaseControl IO según lo requerido por runResourceT. Esto es algo específico de conduit.

Para el CSV ByteString a, necesitamos encontrar qué instancias de CSV. Para hacerlo, vaya al http://hackage.haskell.org/packages/archive/csv-conduit/0.2.1.1/doc/html/Data-CSV-Conduit.html#t:CSV (donde la documentación del paquete es, en mi opinión, un tanto odiosamente todo incluido en la clase de letra ...) y haga clic en Instancias para ver qué instancias disponibles tenemos del formulario CSV ByteString a. Las dos opciones son CSV ByteString ByteString y CSV ByteString Text.

De estos dos, Text es preferible porque maneja unicode y es poco probable que CSV contenga datos binarios. ByteString es más o menos similar a un [Word8] mientras Text es más similar a [Char] que es probablemente lo que quiere. Por lo tanto, a debe ser Text (aunque ByteString seguirá funcionando).

Esto significa que el resultado de la llamada a la función es ResourceT IO [Row Text]. No podemos hacer mucho con esto, pero como ResourceT es un transformador de mónada, podemos "desconectar" fácilmente la capa de transformación de mónada con la función runResourceT. Por lo tanto,

readFile :: FilePath -> IO [Row Text] 
readFile = runResourceT . readCSVFile defCSVSettings 

que es fácilmente utilizable dentro de, digamos, la principal para llegar a la [Row Text] que luego se puede repetir de nuevo con un map o una fold para conseguir sus manos en las filas individuales.

Para ejecutar este tipo de cosas en GHCI, es absolutamente necesario señalar específicamente el tipo. La razón es que la instancia de clase de resultado no depende de ninguno de los parámetros; por lo tanto, para cualquier conjunto de CSVSettings y FilePath, readCSVFile podría devolver cualquier cantidad de tipos diferentes, siempre que ellos como m es una instancia de MonadResource m y a es una instancia de CSV ByteString a. Por lo tanto, debemos señalar explícitamente a GHCi qué tipo desea.

0

Esto funciona con la última versión del paquete csv-conduct (versión 0.6.3). Tenga en cuenta la firma de readCsv sin la cual no pude compilar.

{-# LANGUAGE OverloadedStrings #-} 

import Data.CSV.Conduit 
import Data.Text (Text) 
import qualified Data.Vector as V 
import qualified Data.ByteString as B 

csvset :: Char -> CSVSettings 
csvset c = CSVSettings {csvSep = c, csvQuoteChar = Just '"'} 

readCsv :: String -> Char -> IO (V.Vector (Row Text)) 
readCsv fp del = readCSVFile (csvset del) fp 

main = readCsv "C:\\mydir\\myfile.csv" ';' 
+0

con el paquete csv-conducto-0.6.6 readCsv firma debería ser 'readCsv :: String -> Char -> IO (V.Vector (Fila B.ByteString))', en sustitución de texto de fila con la fila B. ByteString – Janthelme