Using bash to sort data horizontally

Let’s create a function to transpose a file (make rows become columns, and columns become rows):

transpose () {
  awk '{for (i=1; i<=NF; i++) a[i,NR]=$i; max=(max<NF?NF:max)}
        END {for (i=1; i<=max; i++)
              {for (j=1; j<=NR; j++) 
                  printf "%s%s", a[i,j], (j<NR?OFS:ORS)
              }
        }'
}

This just loads all the data into a bidimensional array a[line,column] and then prints it back as a[column,line], so that it transposes the given input. The wrapper transpose () { } is used to store it as a bash function. You just need to copy paste it in your shell (or in ~/.bashrc if you want it to be a permanent function, available any time you open a session).

Then, by using it, we can easily solve the problem by using sort -n -k2: sort numerically based on column 2. Then, transpose back.

$ cat a | transpose | sort -n -k2 | transpose
john sarah mark
5 10 20
z x y

In case you want to have a nice format as final output, just pipe to column like this:

$ cat a | transpose | sort -n -k2 | transpose | column -t
john  sarah  mark
5     10     20
z     x      y

Step by step:

$ cat a | transpose 
sarah 10 x
mark 20 y
john 5 z
$ cat a | transpose | sort -n -k2
john 5 z
sarah 10 x
mark 20 y
$ cat a | transpose | sort -n -k2 | transpose 
john sarah mark
5 10 20
z x y

Leave a Comment