Parte 1
Simplemente d
elija la línea 13:
sed '13d' <file.txt
Y una forma general de hacer el complemento de lo anterior es:
sed '13!d' <file.txt
Parte 2
Porque se puede hacer:
sed -n ':a;${P;q};N;4,$D;ba' <file.txt
Tenga en cuenta que 4
es uno más que el número que necesita. Entonces, si quisieras la última línea 10, esta sería 11
.
Prueba con seq
:
$ seq 100 | sed -n ':a;${P;q};N;4,$D;ba'
98
$
Intento de explicación
:a # define label a
${ # match the last line
P # print the first line of the pattern space
q # quit
}
N # match all lines: append the next line to the pattern
4,${ # match the range of lines 4 to the end of the file
D # delete the first line of the pattern space
}
ba # match all lines: jump back to label a
La valiosa adición de Glenn Jackman:
Esa fue "solo la enésima línea". Aquí está "todo PERO la enésima línea":
sed -n ':a;${s/^[^\n]*\n//;p;q};N;4,${P;D};ba'
funciona con GNU sed, la \n
secuencia puede no funcionar con otros seds.
Intenté esto con BSD sed (OSX) y descubrí que no funcionaba en la forma anterior. Los problemas parecen ser:
;
usado para separar líneas parece funcionar generalmente, pero no funciona después de una etiqueta
- BSD sed parece requerir
;
después del último comando en un {}
grupo de comandos de una línea , mientras que GNU sed no
\n
generalmente se puede usar dentro de la expresión regular, pero aparentemente no dentro de una []
expresión de paréntesis. Entonces, para excluir nuevas líneas, podemos usar algo como [[:alnum:][:punct:][:graph:][:blank:]]
, en cambio, esto puede excluir otros caracteres (específicamente otros caracteres de control).
Entonces este es un intento de una versión más independiente de la plataforma:
sed -n ':a
${s/^[[:alnum:][:punct:][:graph:][:blank:]]*\n//p;q;};N;4,${P;D;};ba'
Esto parece funcionar bajo OSX y Ubuntu.
head
/tail
es mucho más lenta que unased
solución. Gracias sin embargo.head
/tail
) están optimizados para hacer lo que hacen.