Sorting IP Addresses
Problem
You want to sort a list of numeric IP address, but you’d like to sort by the last portion of the number or by the entire address logically.
Solution
To sort by the last octet only (old syntax):
$ sort -t. -n +3.0 ipaddr.list 10.0.0.2 192.168.0.2 192.168.0.4 10.0.0.5 192.168.0.12 10.0.0.20 $
To sort the entire address as you would expect (POSIX syntax):
$ sort -t . -k 1,1n -k 2,2n -k 3,3n -k 4,4n ipaddr.list 10.0.0.2 10.0.0.5 10.0.0.20 192.168.0.2 192.168.0.4 192.168.0.12 $
Discussion
We know this is numeric data, so we use the -n
option. The -t
option indicates the character to use
as a separator between
fields (in our case, a period) so that we can also
specify which fields to sort first. In the first example, we start
sorting with the third field (zero-based) from the left, and the very
first character (again, zero-based) of that field, so +3.0
.
In the second example, we used the new POSIX specification instead of the traditional (but
obsolete) +pos1 -pos2
method. Unlike
the older method, it is not zero-based, so fields start at 1.
$ sort -t . -k 1,1n -k 2,2n -k 3,3n -k 4,4n ipaddr.list
Wow, that’s ugly. Here it is in the old format: sort -t. +0n -1 +1n -2 +2n -3 +3n -4
, which is
just as bad.
Using -t.
to define the field delimiter is the same, but the sort-key fields
are given quite differently. In this case, -k
1,1n
means “start sorting at the beginning of field one
(1)
and (,) stop sorting at the end
of field one (1)
and do a numerical
sort (n)
. Once you get ...
Get bash Cookbook now with the O’Reilly learning platform.
O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.