The cut
command is useful when you want to cut out a specific portion of text lines.
You can do this by character position:
$ ls -l /etc/hosts | cut -c 2-10 rw-r--r--
And you can do this by delimeter (separator symbol). For example, the file /etc/passwd consists of lines with multiple fields of data, separated by the colon (:) symbol. Here, I find the line for my account, and then cut out field 5 (the full name):
$ grep chris /etc/passwd chris:x:1000:1000:Chris Tyler:/home/chris:/bin/bash $ grep chris /etc/passwd|cut -d: -f 5 Chris Tyler
A problem arises when there are multiple fields on a line, and those fields are separated by multiple spaces, such as in this example:
$ w 13:52:48 up 10:25, 5 users, load average: 1.39, 1.36, 1.32 USER TTY FROM LOGIN@ IDLE JCPU PCPU WHAT bylee6 pts/0 10.29.0.44 13:44 8.00s 0.26s 0.07s vim lab5c.py aliakbar pts/1 10.32.8.143 13:43 8.00s 0.11s 0.00s nano loop1.bash chris.ty pts/2 10.31.0.187 12:56 0.00s 0.22s 0.01s w hapancha pts/3 10.29.0.47 13:50 8.00s 0.11s 0.11s -bash rajveer- pts/4 10.29.0.222 13:50 32.00s 0.14s 0.14s -bash
The number of spaces between the fields varies, so that the fields line up vertically; for example, there are three spaces between fields 1 and 2 on the “bylee6” line, but only one space between fields 1 and 2 on the “aliakbar” line.
The cut
command expects only one delimiter between fields, so this presents a problem. Notice that in the following output, the “bylee6” line is not cut properly because of the multiple spaces between field 1 and field 2:
$ w|tail -n +3 |cut -d " " -f2 pts/1 pts/2 pts/3 pts/4
The translate command (tr
) is a useful too which can delete, squeeze, or substitute characters. The squeeze capability is useful here: the command tr -s “ ”
will squeeze multiple consecutive spaces down to a single space. You can then reliably use the cut
command the the delimiter option -d
to select the desired field:
$ w|tail -n +3 |tr -s " " bylee6 pts/0 10.29.0.44 13:44 8.00s 0.26s 0.07s vim lab5c.py aliakbar pts/1 10.32.8.143 13:43 8.00s 0.11s 0.00s nano loop1.bash chris.ty pts/2 10.31.0.187 12:56 0.00s 0.22s 0.01s w hapancha pts/3 10.29.0.47 13:50 8.00s 0.11s 0.11s -bash rajveer- pts/4 10.29.0.222 13:50 32.00s 0.14s 0.14s -bash $ w|tail -n +3 |tr -s " "|cut -d " " -f2 pts/0 pts/1 pts/2 pts/3 pts/4