Leyendo una cadena csv en un array de bash
La siguiente función utiliza awk
para convertir una línea de csv en múltiples líneas. Luego puedo asignar la salida a un arreglo para poder acceder a los campos.
function csv<em>to</em>lines() {
echo $@ | awk '
BEGIN {FPAT = "([^,]*)|(\"[^\"]+\")";}
{for(i=1; i<=NF; i++) {printf("%s\n", $i)}}'
}
line='A,B,"C,D",E'
arr=($(csv<em>to</em>lines $line))
printf '%s,' "${arr[@]}"
Sin embargo, esto no funciona para campos vacíos. Por ejemplo:
line='A,,,,,"C,D",E'
arr=($(csv<em>to</em>lines $line))`
`printf '%s,' "${arr[@]}"
La salida es A,"C,D",E,
pero yo esperaba A,,,,,"C,D",E,
Evidentemente, todas las líneas vacías se ignoran al asignar al arreglo. ¿Cómo puedo crear un arreglo que mantenga las líneas vacías?
davy.ai
Para crear una matriz que mantenga las líneas vacías, puede modificar la función
csv_to_lines
para agregar una comprobación de campos vacíos y reemplazarlos por un marcador antes de asignarlos a la matriz. Aquí hay una versión actualizada de la función:La función actualizada verifica campos vacíos (
$i == ""
) e imprime un marcador (_BLANK_
) en su lugar. El marcador puede ser cualquier cadena que sea poco probable que aparezca en los datos de entrada. La funcióncsv_to_lines
luego reemplaza los campos vacíos con el marcador_BLANK_
antes de asignarlos a la matriz.En el bucle
for
que imprime los elementos de la matriz, verificamos el marcador_BLANK_
e imprimimos una coma en lugar de omitir el elemento. De esta manera, los campos vacíos se conservan en la salida.Con la función actualizada, la línea de entrada
'A,,,,,"C,D",E'
producirá la salida esperada: