How to read first and last line from cat output?
sed Solution:
sed -e 1b -e '$!d' file
When reading from stdin
if would look like this (for example ps -ef
):
ps -ef | sed -e 1b -e '$!d'
UID PID PPID C STIME TTY TIME CMD
root 1931 1837 0 20:05 pts/0 00:00:00 sed -e 1b -e $!d
head & tail Solution:
(head -n1 && tail -n1) <file
When data is coming from a command (ps -ef
):
ps -ef 2>&1 | (head -n1 && tail -n1)
UID PID PPID C STIME TTY TIME CMD
root 2068 1837 0 20:13 pts/0 00:00:00 -bash
awk Solution:
awk 'NR==1; END{print}' file
And also the piped example with ps -ef
:
ps -ef | awk 'NR==1; END{print}'
UID PID PPID C STIME TTY TIME CMD
root 1935 1837 0 20:07 pts/0 00:00:00 awk NR==1; END{print}
sed -n '1p;$p' file.txt
will print 1st and last line of file.txt .
A funny pure Bash≥4 way:
cb() { (($1-1>0)) && unset "ary[$1-1]"; }
mapfile -t -C cb -c 1 ary < file
After this, you'll have an array ary
with first field (i.e., with index 0
) being the first line of file
, and its last field being the last line of file
. The callback cb
(optional if you want to slurp all lines in the array) unsets all the intermediate lines so as to not clutter memory. As a free by-product, you'll also have the number of lines in the file (as the last index of the array+1).
Demo:
$ mapfile -t -C cb -c 1 ary < <(printf '%s\n' {a..z})
$ declare -p ary
declare -a ary='([0]="a" [25]="z")'
$ # With only one line
$ mapfile -t -C cb -c 1 ary < <(printf '%s\n' "only one line")
$ declare -p ary
declare -a ary='([0]="only one line")'
$ # With an empty file
$ mapfile -t -C cb -c 1 ary < <(:)
declare -a ary='()'