2011-11-18 9 views
66

Tengo varios archivos que quiero concat con cat. DigamosConcatenar archivos e insertar nueva línea entre archivos

File1.txt 
foo 

File2.txt 
bar 

File3.txt 
qux 

Quiero concat para que el archivo final será similar a:

foo 

bar 

qux 

En lugar de esto con habitual cat File*.txt > finalfile.txt

foo 
bar 
qux 

Cuál es la forma correcta de hacerlo?

+2

posible duplicado de [¿Cómo puedo incluir una línea en blanco entre los archivos que estoy concatenación wi th "cat"?] (http://stackoverflow.com/questions/1653063/how-do-i-include-a-blank-line-between-files-im-concatenating-with-cat) – legoscia

Respuesta

63

que puede hacer:

for f in *.txt; do (cat "${f}"; echo) >> finalfile.txt; done 

Asegúrese de que el archivo no existe finalfile.txt antes de ejecutar el comando anterior.

Si está permitido el uso de awk que puede hacer:

awk 'FNR==1{print ""}1' *.txt > finalfile.txt 
+3

'AWK '{ imprime $ 0} '* .txt' – timger

+3

por 'AWK' te refieres a' awk', ¿no? –

+5

Esto tiene el defecto distintivo de que habrá líneas vacías al final (de la primera alternativa) o al principio (segunda alternativa). Sin embargo, puedes evitar esto fácilmente con 'awk 'FNR == 1 && NR> 1 ...' '. – tripleee

21

Si se tratara de mí haciendo que haría uso de sed:

sed -e '$s/$/\n/' -s *.txt > finalfile.txt 

En este patrón sed $ tiene dos significados, en primer lugar, coincide con el último número de línea (como un rango de líneas para aplicar un patrón) y, en segundo lugar, coincide con el final de la línea en el patrón de sustitución.

Si su versión de sed no tiene (archivos de entrada de proceso por separado) -s puede hacerlo todo como un bucle sin embargo:

for f in *.txt ; do sed -e '$s/$/\n/' $f ; done > finalfile.txt 
+2

O en GNU sed: 'sed -s '$ G' * .txt> finalfile.txt' –

+0

¡Solo una transmisión! esta debería ser la respuesta aceptada! –

24

Si usted tiene algunos archivos suficientes que puede enumerar cada uno, entonces usted puede utilizar process substitution en Bash, la inserción de una nueva línea entre cada par de archivos:

cat File1.txt <(echo) File2.txt <(echo) File3.txt > finalfile.txt 
+0

¡Hermoso! Gracias. –

6

Así es como yo sólo lo hizo en OSX 10.10.3

for f in *.txt; do (cat $f; echo '') >> fullData.txt; done 

ya que el simple comando 'echo' sin params terminó en ninguna nueva línea insertada.

4

Esto funciona en Bash:

for f in *.txt; do cat $f; echo; done 

En contraste con respuestas con >> (append), la salida de este comando se puede inyectar en otros programas.

Ejemplos:

  • for f in File*.txt; do cat $f; echo; done > finalfile.txt
  • (for ... done) > finalfile.txt (parens son opcionales)
  • for ... done | less (tuberías en menos)
  • for ... done | head -n -1 (esto se despoja de la línea en blanco al final)
3

En python, esto se concatena con líneas en blanco archivos (los , suprime la adición de una línea en blanco de salida adicional):

print '\n'.join(open(f).read() for f in filenames), 

Aquí es el pitón feo de una sola línea que se puede llamar de la cáscara e imprime la salida a un archivo:

python -c "from sys import argv; print '\n'.join(open(f).read() for f in argv[1:])," File*.txt > finalfile.txt 
3

Puede hacerlo utilizando xargs si se quiere, pero la idea principal sigue siendo el mismo:

find *.txt | xargs -I{} sh -c "cat {}; echo ''" > finalfile.txt 
+0

Gracias. Encuentro 'xargs' mucho más fácil de usar que los loops en bash. – RawwrBag

Cuestiones relacionadas