1

I am trying to sort the listing of directories by starting with the second character.

For example, if I do the code below, the listing of the directories are in order based on the first character.

$ ls -1d */
lrodriguez/
mreynolds/
yalberto/

What I want to accomplish is to display them as:

yalberto/
mreynolds/
lrodriguez/

I've looked at the following forum: How to sort files by part of the filename? but had no success.

I have tried something like: ls -1d -- *?[a-z]* | sort -t?[a-z] -k2 but didn't get any results. Pretty new to the Unix environment and any pointers will be very helpful. Thank you in advance.

2 Answers2

3

With sort, you can use a key of the form F.C to specify a character position within a field. So for example

$ printf '%s\n' */ | sort -k1.2
yalberto/
mreynolds/
lrodriguez/

Note that this will fail if any of the directory names contains a newline.

That could be worked around with GNU sort by working with NUL-delimited records instead with:

printf '%s\0' */ | sort -zk1.2 | tr '\0' '\n'

Also note that the expansion of */ also includes symlinks to directories.

steeldriver
  • 81,074
2

With zsh:

print -rC1 -- *(N/oe['REPLY=${REPLY#?}'])
  • print -rC1 prints its arguments raw on 1 Column
  • *(qualifiers): glob with glob qualifiers
  • N: Nullglob: expands to nothing if there's no match
  • /: only select files of type directory
  • oe[expression]: order the list based on the result of the expression (of the value of $REPLY initially containing the file name after it's been manipulated by the expression)
  • REPLY=${REPLY#?}: strip the first character off the file name.

You may also want to add the first character at the end like with REPLY=${REPLY#?}.$REPLY[1] so that asmith, bsmith, csmith sort in that order instead of randomly.