Fusionar múltiples archivos CSV sin fusionar el encabezado


21

Necesito fusionar múltiples archivos .CSV (usando el catcomando) pero sin copiar el encabezado de cada archivo.

¿Cuál es la mejor manera de lograr esta tarea?

Respuestas:


32

Necesitará más que el catcomando, como se describe aquí :

Digamos que tiene 3 archivos CSV: file1.csv, file2.csv, y file3.csvy desea unirse a ellos para bigfile.csvy su cabecera es siempre (sólo) la primera línea, a continuación, el uso

bien (mantener el encabezado del primer archivo "file1.csv"):

cat file1.csv <(tail +2 file2.csv) <(tail +2 file3.csv) > bigfile.csv

o (elimine el encabezado de todos los archivos cuyos nombres comienzan con "archivo"):

awk 'FNR > 1' file*.csv > bigfile.csv

44
Encontré esto buscando una respuesta genérica de Linux, pero en mi caso esto no funcionó exactamente. Silenciosamente ignoraría file1.csv. Necesitaba atrapar ese archivo. cat <(cat file1.csv) <(tail +2 file2.csv) <(tail +2 file3.csv) > bigfile.csv
Lelon

Estoy obteniendo tail + 2: comando no encontrado cuando utilicé cat <file1.csv <(tail +2 file2.csv) <(tail +2 file3.csv)> método

@ user64636 debe haber un espacio entre la cola y +2
nohillside

De hecho, tuve que usar tail -n+2, tail +2no funcionaría
Matthieu Napoli

12

Estoy de acuerdo con la respuesta principal, pero sugiero extenderla con el siguiente escenario (ya que no puedo comentar):

Si desea que el archivo de salida contenga encabezado (una vez), el script correcto es:

awk '(NR == 1) || (FNR > 1)' file*.csv > bigfile.csv

FNR representa el número del registro procesado en un solo archivo. Y NR lo representa globalmente, por lo que se acepta la primera línea y el resto se ignora como antes.


6

También puede usar un comando de grupo ( { ; }) en lugar de la sustitución de proceso ( <()):

{ head -n1 file1.csv; for f in file*.csv; do tail -n+2 "$f"; done; } > new.csv

También funciona con terminaciones de línea CRLF siempre que los archivos terminen con una línea vacía ( \r\n).

POSIX 1003.1-2001 dejó obsoletas las versiones de solo cabeza y cola, y generan advertencias en algunos entornos.


2

Necesario para concatenar dos CSV grandes con columnas idénticas en CSV más grandes para la secuencia de comandos de fragmentación (los datos no tienen identificadores únicos).

Primero sacó el encabezado del segundo csv

awk 'FNR > 1' file2.csv > file2_noheading.csv

A continuación, concatenado a través de lo siguiente

cat file1.csv file2_noheading.csv > newfile.csv

1

El uso de la secuencia de comandos anterior dio como resultado un archivo similar a este:

header,of,csv1
contents,of,csv1
==> csv2.csv

contents,of,csv2

Para convertirlo en un CSV adecuado, con una línea de encabezado y todos los valores relevantes, empleé el siguiente sedencantamiento ...sed -ie "/^$/d;/^==>/d" bigfile.csv


0

Solución más fácil si tiene una tonelada de archivos:

awk 'FNR > 1' *.csv > merged.csv

Simplemente regrese para editar el archivo grande y agregue el encabezado nuevamente.


¿En qué se diferencia su respuesta de lo que fue presentado por iolsmit en 2013 awk 'FNR > 1' file*.csv > bigfile.csv? ¡No es!
user3439894

Re: ¿cómo es diferente? Es una respuesta más concisa y la que copié y pegué, al menos:) Obtiene mi voto a favor
Rick Davies

Esta es una buena respuesta, porque no necesita todos los archivos para comenzarfile
big_smile
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.