awk cuando tanto el delimitador como las comillas se usan para un campo

Tengo un file en el siguiente formatting:

field1|field2|field3 field1|"field2|field2"|field3 

Observe que la segunda fila contiene comillas dobles. La cadena dentro de las comillas dobles pertenece al campo 2. ¿Cómo se extrae esto usando awk? He estado buscando en Google sin resultados. Intenté esto sin suerte también

 FS='"| "|^"|"$' '{print $2}' 

Si tienes una versión reciente de gawk , estás de suerte. FPAT function FPAT , documentada aquí

 awk 'BEGIN { FPAT = "([^|]+)|(\"[^\"]+\")" } { print "NF = ", NF for (i = 1; i <= NF; i++) { sub(/"$/, "", $i); sub(/^"/, "", $i);printf("$%d = %s\n", i, $i) } }' file NF = 3 $1 = field1 $2 = field2 $3 = field3 NF = 3 $1 = field1 $2 = field2|field2 $3 = field3 

Esto es algo que obtienes en csv : si el delimitador es parte del campo, se cotiza. De repente, la tarea de analizarlo MUCHO más difícil, porque no se puede dividir en un delim.

Afortunadamente, si perl es una opción, tiene el module Text::CSV que maneja este caso:

 #!/usr/bin/env perl use strict; use warnings; use Text::CSV; my $csv = Text::CSV -> new ( { 'sep_char' => '|' } ); while ( my $row = $csv -> getline ( *STDIN ) ) { print $row -> [1],"\n"; } 

Probablemente podría condensar esto en una línea / pipeable si lo prefiere, algo así como:

 perl -MText::CSV -e 'print map { $_ -> [1] ."\n" } @{ Text::CSV -> new ( { 'sep_char' => '|' } ) -> getline_all ( *ARGV )}; 

Es posible que desee formatear esta información con sed para que pueda ser analizada por awk más fácilmente. por ejemplo:

 $ sed 's/"//g' awktest1.txt field1|field2|field3 field1|field2|field2|field3 $ sed 's/"//g' awktest1.txt > awktest2.txt $ awk 'BEGIN {FS = "|"} ; {print $2}' awktest2.txt field2 field2 

Pero, nuevamente, no conozco la naturaleza de los datos con los que está trabajando.