Respuestas:
La razón por la que file.txt está vacío después de ese comando es el orden en que el shell hace las cosas. Lo primero que sucede con esa línea es la redirección. El archivo "file.txt" se abre y trunca a 0 bytes. Después de eso, se ejecuta el comando sed, pero en ese momento el archivo ya está vacío.
Hay algunas opciones, la mayoría implica escribir en un archivo temporal.
sed '1d' file.txt > tmpfile; mv tmpfile file.txt # POSIX
sed -i '1d' file.txt # GNU sed only, creates a temporary file
perl -ip -e '$_ = undef if $. == 1' file.txt # also creates a temporary file
ed
.
ed
comando sería: printf "%s\n" 1d w q | ed file.txt
(I heart ed)
-exec sed -i '1d' {} \;
Una opción alternativa muy liviana es simplemente 'ajustar' todo menos la primera línea (esta puede ser una forma fácil de eliminar encabezados de archivos en general):
# -n +2 : start at line 2 of the file.
tail -n +2 file.txt > file.stdout
Siguiendo a @Evan Teitelman, puedes:
tail -n +2 file.txt | sponge file.txt
Para evitar un archivo temporal. Otra opción podría ser:
echo "$(tail -n +2 file.txt)" > file.txt
Etcétera. Prueba de la última:
[user@work ~]$ cat file.txt
line 1
line 2
line 3
line 4
line 5
[user@work ~]$ echo "$(tail -n +2 file.txt)" > file.txt
[user@work ~]$ cat file.txt
line 2
line 3
line 4
line 5
[user@work ~]$
Vaya, perdimos una nueva línea (según el comentario de @ 1_CR a continuación), intente en su lugar:
printf "%s\n\n" "$(tail -n +2 file.txt)" > file.txt
[user@work ~]$ cat file.txt
line 1
line 2
line 3
line 4
line 5
[user@work ~]$ printf '%s\n\n' "$(tail -n +2 file.txt)" > file.txt
[user@work ~]$ cat file.txt
line 2
line 3
line 4
line 5
[user@work ~]$
Volviendo a sed, intente:
printf '%s\n\n' "$(sed '1d' file.txt)" > file.txt
o quizás
echo -e "$(sed '1d' file.txt)\n" > file.txt
Para evitar efectos secundarios.
tail
truco funcionó para mí (tardó menos de 3 segundos en un archivo de 130 MB). ¡Gracias!
echo "$(tail -n +2 file.txt)" > file.txt
Es la respuesta perfecta.
También echa un vistazo a sponge
partir
moreutils
. sponge
absorbe los datos de la entrada estándar hasta que el final de escritura de la entrada estándar se cierra antes de escribir en un archivo. Se usa así:
sed '1d' file.txt | sponge file.txt
Este tema es de interés, por lo que pruebo el punto de referencia de 3 maneras:
sed '1d' d.txt > tmp.txt
tail -n +2 d.txt > tmp.txt
sed -i '1d' d.txt
Tenga en cuenta que el objetivo d.txt
es un archivo de 5.4GB
Obtén el resultado:
run 1 : sed '1d' d.txt > r1.txt
14s
run 2 : tail -n +2 d.txt > r2.txt
20s
run 3 : sed -i '1d' d.txt
88s
Conclusión: a continuación parece ser la forma más rápida:
sed '1d' file.txt > tmpfile; mv tmpfile file.txt
sed '1d' d.txt
método no incluyó (o eso parece al leer sus pruebas) el mv
comando. En mis pruebas en FreeBSD con un archivo de 20 MB, sed -i
fue el más rápido.
ex
se puede usar para una verdadera edición in situ que no involucra un archivo temporal
ex -c ':1d' -c ':wq' file.txt
strace -e open ex -c ':1d' -c ':wq' foo
. ex trunca el archivo original con el archivo temporal, mientras que la opción -i de GNU sed sobrescribe el original con el archivo temporal. No estoy seguro de cómo funciona el sed de BSD.
Puede usar Vim en modo Ex:
ex -s -c '1d|x' file.txt
1
encontrar la primera línea
d
Eliminar
x
guardar y cerrar
Este comando eliminará 1 línea y guardará como "file.txt".
sed '1d' file.txt > /tmp/file.txt && mv /tmp/file.txt file.txt || rm -f /tmp/file.txt
Para eliminar una línea de praticiler en el archivo
Archivo Sed '1d'
Archivo Sed '1d3d'
Eliminar personaje en línea
1 Eliminar los dos primeros charter en lin
Archivo de Sed /^..//
2 Eliminar las dos últimas líneas de chrectercina
Archivo de Sed / .. £ //
3 Eliminar línea en blanco
Archivo Sed '/ ^ £ / d'
£
≠ $
.
Podría usar vim para hacer esto:
vim -u NONE +'1d' +wq! /tmp/test.txt
cat file01 | sed -e '1,3d'
// muestra contenido en el archivo 01 pero elimina la primera y tercera línea
sed
, puede usarsed -i .bak '1d' file.txt
.