¿Cómo editar múltiples archivos de texto con un solo comando?

18

Quiero eliminar la primera línea de múltiples archivos de texto y reemplazarla con otra línea. ¿Hay alguna manera de hacer esto usando la terminal?

Sé cómo usar vim, ¿hay alguna forma de automatizarlo? Quiero evitar hacerlo manualmente (como al editar cada archivo individualmente).

Si es posible, me gustaría evitar instalar nuevas bibliotecas (especialmente para algo como lo que considero muy simple, pero podría estar equivocado).

¡Gracias por adelantado!

TomTsagk
fuente

Respuestas:

21

Puedes usar sed:

sed -i.bak '1s/^.*$/new line/' *.txt

Esto reemplazará la primera línea de todos los .txtarchivos en el directorio actual con el texto new line, cámbielo para satisfacer sus necesidades.

También se hará una copia de seguridad de los archivos originales con .bakextensión, si no lo desea, simplemente use:

sed -i '1s/^.*$/new line/' *.txt
heemayl
fuente
¡Gracias! sedes en realidad lo que estaba buscando!
TomTsagk
@TomTsagk Me alegro de poder ayudar :)
heemayl
11

Bueno, usándose a vimsí mismo:

vim -Nesc 'bufdo call setline(1,"This is the replacement.") | wq' file1 file2 ...

Lo que esto hace:

  • setline (n, text), bueno, es una función que establece la línea nen text.
  • call es necesario para llamar a funciones.
  • bufdo se usa para repetir un comando entre buffers (sin un rango, actúa en todos los buffers).
  • wqguarda y sale del búfer. Necesitamos hacer esto antes de pasar al siguiente búfer, por lo que este comando se encadena al callcomando usando |.
  • -c cmdejecuta cmdes un comando en modo comando después de cargar el primer búfer.
  • Nes activa el modo no compatible, silencioso y ex, que es mejor para el procesamiento no interactivo.

Beneficios:

  • El setlinecontenido del texto puede ser cualquier cosa - una &en un sedtexto de reemplazo puede tener efectos no deseados.
muru
fuente
sedParece mucho más fácil de usar, ¡pero es realmente increíble que vimpueda hacer lo mismo! ¡Muchas gracias por tu respuesta!
TomTsagk
@TomTsagk bueno, solo quería ilustrar cómo podrías actuar en varios archivos ( bufdo). Considere que ya tiene los archivos abiertos y ... Y para mostrar una alternativa 1s/foo/bar/.
Muru
Awesoming !!! <3_ <3
Campa
3

Algunas otras opciones:

  • awk(necesita una versión relativamente nueva de GNU awk)

    $ awk -i inplace -vline="new line" '(FNR==1){print line; next}1;' *.txt
    
  • Perl / shell

    $ for f in *txt; do
        perl -i -lne '$.==1 ? print "new line" : print' "$f"
      done
    
  • Shell / coreutils

    $ for f in *txt; do 
        ( echo "new line"; tail -n+2 "$f" ) > foo && mv foo "$f"; 
      done
    
terdon
fuente
2

Este script hará lo que solicitó, colocando los archivos modificados en un nuevo directorio sin cambiar realmente los originales.

d=/tmp/cooked
mkdir $d
for f in *  #will match all files in current directory; adjust as desired
do
  echo "This is the new 1st line" > /${d}/${f}
  sed 1d ${f} >> /${d}/${f}
done
Charles Boling
fuente
Estaba respondiendo lentamente (probé mi código) ... ¡y me gusta mucho la solución de heemayl!
Charles Boling
0

Utilizando gawk

gawk -i inplace 'FNR==1 {$_="your_replacement"}; {print}' *.txt

Ejemplo

% cat foo.txt 
1
2
3
4

% cat bar.txt 
1
2
3
4

% gawk -i inplace 'FNR==1 {$_="your_replacement"}; {print}' *.txt

% cat foo.txt                                                    
your_replacement
2
3
4

% cat bar.txt                                                    
your_replacement
2
3
4
AB
fuente
0

jEdit: Lo uso para buscar y reemplazar en masa. Es potente con la capacidad de usar RegEx - Expresiones regulares. Puede operar en archivos dentro de un directorio, especificar extensiones de archivo, por ejemplo, ".html", etc. Y puede ver la configuración regional del cambio de candidato en contexto, en una GUI. jEdit es genial.

jEdit está disponible a través del centro de software de Ubuntu.

Roger
fuente
0

Los comandos tail y cat harían esto fácilmente:

tail -n +1 $file > tmpfile
cat newfirstline tmpfile >$file

Envuelva esos en un bucle adecuado y tal vez use un archivo temporal adecuado y justo en lugar de un nombre de archivo temporal codificado. Creo que bash y otros shells tienen una sintaxis para crear archivos temporales.

La opción -n de tail tiene dos interpretaciones dependiendo de si el argumento tiene un signo más. Si tiene un signo más, significa mostrar la cola del archivo comenzando en el número de línea dado. De lo contrario, el número es el número de líneas, incluida la última línea, que se supone que debe generar esa cola.

hombre espacio cardiff
fuente