2011-12-22 37 views
5

estoy usando rubí 1,9 a analizar el siguiente archivo csv con MacRoman caráctercsv de análisis por comas, comillas dobles y codificación

# encoding: ISO-8859-1 
#csv_parse.csv 
Name, main-dialogue 
"Marceu", "Give it to him ó he, his wife." 

me hizo lo siguiente para analizar esto.

require 'csv' 
input_string = File.read("../csv_parse.rb").force_encoding("ISO-8859-1").encode("UTF-8") 
#=> "Name, main-dialogue\r\n\"Marceu\", \"Give it to him \x97 he, his wife.\"\r\n" 

data = CSV.parse(input_string, :quote_char => "'", :col_sep => "/\",/") 
#=> [["Name, main-dialogue"], ["\"Marceu", " \"Give it to him \x97 he, his wife.\""]] 

Así, el problema es la segunda matriz de datos es de una sola cadena en lugar de 2 cadenas como: ["\"Marceu\"", " \"Give it to him \x97 he, his wife.\""]] he intentado con :col_sep => "," (que es el comportamiento por defecto) pero me dio 3 divisiones.

header = CSV.parse(input_string, :quote_char => "'")[0].map{|a| a.strip.downcase unless a.nil? } 
#=> ["Name", "main-dialogue"] 

Tengo que analizar de nuevo el encabezado ya que no hay comillas dobles aquí.

La salida está pensada para mostrarse en el navegador de nuevo, por lo que el carácter ó debe aparecer como de costumbre y no como \x97 u otro.

¿Hay alguna manera de resolver los problemas anteriores?

+0

¿Por qué utiliza [ISO-8859-1] (http://en.wikipedia.org/wiki/ISO-8859-1#ISO- 8859-1) cuando sabes el la codificación es [MacRoman] (http://en.wikipedia.org/wiki/MacRoman)? No son lo mismo. –

+0

Gracias por señalarlo. Lo intenté con MacRoman pero el resultado es el mismo que me da una sola división en lugar de dos. Quería obtener la mayor cantidad posible de personajes latinos, lo que me llevó a elegir ISO-8859-1 que también dio 'input_string.valid_encoding?'. ¡Por favor corrígeme si estoy equivocado! – zoras

Respuesta

8

Creo que tiene MacRoman datos codificados; si lo hace en irb:

>> "\x97".force_encoding('MacRoman').encode('UTF-8') 

se obtiene lo siguiente:

=> "ó" 

y que parece ser el personaje que usted está esperando. Por lo que desea esto:

input_string = File.read("../csv_parse.rb").force_encoding('MacRoman').encode('UTF-8') 

Entonces usted tiene dos columnas en el archivo CSV, las columnas se citan con comillas dobles (por lo que no es necesario :quote_char), y el delimitador es ', ' así que esto debería funcionar:

data = CSV.parse(input_string, :col_sep => ", ") 

y data se verá así:

[ 
    ["Name", "main-dialogue"], 
    ["Marceu", "Give it to him ó he, his wife."] 
] 
+0

Gracias por la solución, sabía que estaba cerca. :) Por cierto, estaba tratando de cambiar MacRoman con la codificación del archivo fuente csv, ¿podemos detectarlo? – zoras

+0

@zoras: Detectar la codificación es difícil y generalmente es un montón de trabajo de adivinar. UTF-8 tiene una estructura interna que puede intentar detectar, otros juegos de caracteres tienen espacios en diferentes lugares (por ejemplo, MacRoman tiene 0x80 pero ISO-8859-1 no), etc. Hay [rchardet] (https: // github. com/kirillrdy/rchardet) pero nunca lo he usado. –

0

Me parece que está utilizando las opciones :quote_char y :col_sep incorrectamente.

La primera debería ser que el carácter que se utiliza para encerrar campos, es decir, '"' para los datos que has demostrado, y :col_sep debe ser sólo ","

Las comillas dobles que se muestran en el último ejemplo se acaba de formatear el rubí salida para ti.

+0

Lo probé pero me sale este error .. 'ruby-1.9.2-p180/lib/ruby ​​/ 1.9.1/csv.rb: 1895: en bloque (2 niveles) en shift ': citas ilegales en la línea 2 .(CSV :: MalformedCSVError) ' – zoras

+0

¿Por qué no usa UTF-8? –

+0

Los usuarios de mi aplicación cargan el archivo csv y algunos de ellos quieren soporte de codificación. Entonces, estoy buscando 'input_string.valid_encoding?' Y convirtiéndolos a ISO-8859-1 como se indica arriba. Para UTF-8, acabo de leer el archivo. ¿No es esta la manera correcta? – zoras

Cuestiones relacionadas