Tengo un archivo llamado que Element_query
contiene el resultado de una consulta:
SQL> select count (*) from element;
[Output of the query which I want to keep in my file]
SQL> spool off;
Quiero eliminar la primera línea y la última línea usando el comando de shell.
Respuestas:
Usando GNU
sed
:Cómo funciona :
-i
opción editar el archivo en sí. También puede eliminar esa opción y redirigir la salida a un nuevo archivo u otro comando si lo desea.1d
elimina la primera línea (1
para actuar solo en la primera línea,d
para eliminarla)$d
elimina la última línea ($
para actuar solo en la última línea,d
para eliminarla)Ir más lejos :
1,5d
eliminaría las primeras 5 líneas.SQL>
uso de la declaración/^SQL> /d
/^$/d
statement1;statement2;satement3;...
) o especificándolas por separado en la línea de comando (-e 'statement1' -e 'statement 2' ...
)fuente
1,3d
eliminará las primeras tres líneas) pero es un poco más difícil para el final. Dependiendo de lo que desee, podría ser mejor usar esto:sed -i '/^SQL> /d' Element_query
para eliminar líneas que comienzanSQL>
sin importar dónde se encuentre en el archivo.sed
trazador de líneas, que funcionará para eliminar los recuentos de líneas arbitrarias del encabezado y la cola de un archivo. Sin embargo, siempre que la entrada sea un archivo normal, es solo agrupar una sola entrada en doshead
procesos: es el La forma más rápida de hacer esto por lo general.sed -i '1d' table-backup.sql
eliminar la primera línea del archivo de texto SQLcabeza; cabeza
Con lo anterior, puede especificar el primer número de líneas para eliminar del encabezado de la salida con el primer
head
comando, y el número de líneas para escribiroutfile
con el segundo. Por lo general, también lo hará más rápido quesed
, especialmente cuando la entrada es grande , a pesar de requerir dos invocaciones. Dondesed
sin duda debe ser preferido, sin embargo, es en el caso de que<infile
es no un habitual, lseekable archivo - porque esto normalmente no funciona como es debido, en ese caso, perosed
puede manejar todas las modificaciones de salida en un solo proceso, con guión.Con un GNU
head
también puede usar la-
forma negativa[num]
en el segundo comando. En cuyo caso, el siguiente comando eliminará la primera y última línea de la entrada:O con un POSIX
sed
:Digamos, por ejemplo, que estaba leyendo una entrada de 20 líneas y quería eliminar las primeras 3 y las últimas 7. Si resolviera hacerlo con /
sed
, lo haría con un buffer de cola. Primero sumaría tres y siete para un recuento total de diez y luego hago:Ese es un ejemplo que elimina las primeras 3 y las últimas 7 líneas de la entrada. La idea es que puede almacenar tantas líneas como desee de la cola de entrada en el espacio del patrón en una pila, pero solo
P
borre la primera de estas para cada línea extraída.1,10
sed
P
no hay nada porque para cada una de ellas está apilando la entrada en el espacio del patrón línea por línea en unb
bucle de rancho.sed
sed
elige toda la pila , por lo que las primeras 3 líneas se eliminan de la salida de una sola vez.sed
llega a la$
última línea de entrada e intenta extraer laN
extensión, golpea EOF y detiene el procesamiento por completo. Pero en ese momento el espacio del patrón contiene todas las líneas14,20
, ninguna de las cuales ha sidoP
borrada y nunca lo ha sido.sed
P
alinea solo hasta la primera línea de flujo que ocurre\n
en el espacio del patrón, yD
elige lo mismo antes de comenzar un nuevo ciclo con lo que queda, o las siguientes 6 líneas de entrada. La séptima línea se agrega nuevamente a la pila con elN
comando ext en el nuevo ciclo.Y así, de
seq
la salida de (que es 20 líneas numeradas secuencialmente) ,sed
solo imprime:Esto se vuelve problemático cuando el número de líneas que desea eliminar de la cola de entrada es grande, porque
sed
el rendimiento es directamente proporcional al tamaño de su espacio de patrón. Aún así, sin embargo, es una solución viable en muchos casos, y POSIX especifica unsed
espacio de patrón para manejar al menos 4 kb antes de reventar.fuente
tail
también admite latail -n+<num>
sintaxis extendida que significa "comenzar desde la línea<num>
"No voy a responder cómo eliminar varias líneas. Voy a atacar el problema de esta manera:
grep -v '#SQL>' Element_query >outfile
En lugar de contar líneas, elimina los comandos SQL al reconocer las solicitudes. Esta solución se puede generalizar para otros archivos de salida de sesiones SQL con más comandos que solo dos.
fuente
ed
es 'el editor de texto estándar' y debería estar disponible en sistemas que no tienen GNUsed
. Originalmente fue diseñado como un editor de texto, pero se adapta bien a los scripts.1d
elimina la primera línea del archivo,$d
(citado para que el shell no piense que es una variable) elimina la última línea,w
escribe el archivo y seq
cierraed
.printf
aquí se usa para formatear los comandos paraed
: cada uno debe ir seguido de una nueva línea; Por supuesto, hay otras formas de lograr esto.fuente
Hay varias formas de eliminar las líneas iniciales y finales de un archivo.
Puede usarlo
awk
ya que maneja la coincidencia de patrones y el recuento de líneas,Puede usar
grep -v
para excluir líneas que no desea por patrón, y puede hacer coincidir múltiples patrones usando la-E
opción,Puede usar
head
ytail
para recortar recuentos específicos de líneas,Puede usar
vi/vim
y eliminar la primera y la última línea (s),podría usar un script en perl, omitir la primera línea, guardar cada línea, imprimir cuando obtenga una línea siguiente,
fuente
head
realidad, no necesita la tubería y, de hecho, es mejor no usarla si puede salirse con la suya. Cuando lo hagahead | head
, aunque los dos procesos pueden ejecutarse simultáneamente, ambos procesan prácticamente todos los mismos datos de forma redundante. Si lo hace{ head >dump; head >save; } <in
, solo salta por desplazamiento: el primero lee 10 líneas>dump
y el segundo lee las siguientes 10 líneas>save
.Sería mucho mejor servir cortando los comandos SQL. Puede hacer esto de dos maneras:
Si está absolutamente seguro de que la secuencia "
SQL>
" no aparece en ningún otro lugar de la salida,Si no estás tan seguro,
La segunda versión es más lenta pero más precisa: ignorará las líneas que comienzan exactamente con "SQL>" y terminan en punto y coma, que parecen describir las líneas que desea eliminar.
Sin embargo, sería mejor no incluir esa salida adicional en el archivo para empezar. La mayoría de los sistemas SQL tienen alguna forma de hacerlo. No estoy muy familiarizado con Oracle, pero tal vez esta respuesta podría ser útil.
fuente
Puede seleccionar las líneas entre un rango en
awk
(esto supone que sabe cuántas líneas hay):O en Perl:
Si no sabe cuántas líneas hay, puede calcularlas sobre la marcha usando
grep
(tenga en cuenta que esto no contará las líneas en blanco, usegrep -c '' file
para contarlas también):fuente
Prueba esta solución:
Personalización
Puede adaptarlo fácilmente para eliminar las n primeras líneas cambiando el
+2
detail
;o para eliminar las últimas n líneas cambiando el
-1
dehead
.fuente
Utilizando
awk
:< inputfile
: redirige el contenido deinputfile
toawk
'sstdin
> outputfile
: redirige el contenido deawk
'sstdout
aoutputfile
NR>1
: ejecuta las siguientes acciones solo si el número del registro que se procesa es mayor que 1{print r}
: imprime el contenido de la variabler
{r=$0}
: asigna el contenido del registro que se procesa a la variabler
Entonces, en la primera ejecución del
awk
script, el primer bloque de acciones no se ejecuta, mientras que el segundo bloque de acciones se ejecuta y el contenido del registro se asigna a la variabler
; en la segunda ejecución, se ejecuta el primer bloque de acciones yr
se imprime el contenido de la variable (por lo que se imprime el registro anterior); Esto tiene el efecto de imprimir cada línea procesada pero la primera y la última.fuente
r
.