Sort::Fields(3pm)

πŸ“¦
version 1.003 Β· 4 versions
, in debian trixie, ubuntu resolute, ubuntu stonking

πŸ’– Sort::Fields β€” bestie edition πŸ’–

okay so this is the Sort::Fields page from the Perl manual (perl v5.40.1, and yeah it's in the User Contributed Perl Documentation section, iykyk). Sit down, grab a lil drink, we're sorting lines with fields in them and it's gonna be so good. ✨


🌸 NAME 🌸

Sort::Fields β€” sort lines that have data separated into fields. that's it. that's the whole vibe. πŸ’…


✨ SYNOPSIS ✨

use Sort::Fields;
@sorted = fieldsort [3, '2n'], @lines;
@sorted = fieldsort '\+', [-1, -3, 0], @lines;

$sort_3_2n = make_fieldsort [3, '2n'], @lines;
@sorted = $sort_3_2n->(@lines);

πŸ¦‹ DESCRIPTION πŸ¦‹

Sort::Fields is your general-purpose, super efficient way to sort lists of lines where the data is split up into fields. It's giving organizational queen. πŸ‘‘

When you use it, it auto-imports two subroutines β€” fieldsort and make_fieldsort β€” plus two variants, stable_fieldsort and make_stable_fieldsort. No cap, they just show up. 🫢

  • make_fieldsort builds a sorting subroutine for you and hands you back a reference to it.
  • fieldsort is literally just a wrapper around the make_fieldsort subroutine.

So here's the tea on the arguments:

The first argument to make_fieldsort is a delimiter string, and it gets used as a regular expression argument for a split operator. It's optional bestie! If you don't hand one over, make_fieldsort splits each line using /\s+/.

The second argument is an array reference holding one or more field specifiers. These specifiers are the whole point β€” they tell the sort which fields in the strings get used to sort the data:

  • 1 means the first field, 2 means the second, and so on down the line.
  • A negative specifier like -2 means sort on the second field in reverse (descending) order.
  • Want numeric instead of alphabetic comparison? Append n to the specifier. slay.
  • A specifier of 0 means the entire string (-0 means the entire string, in reverse order). periodt.

The order the specifiers show up in is the order they get used to sort the data. Primary key first, secondary key second, and so on. main character energy goes to the first one. 🌟

fieldsort [1, 2], @data is roughly equivalent to make_fieldsort([1, 2])->(@data).

⚠️ Do not call fieldsort over and over again with the same sort specifiers, bestie. If you need a particular sort more than once, it's way more efficient to call make_fieldsort one single time and reuse the subroutine it returns. trust. πŸ’€

And finally: stable_fieldsort and make_stable_fieldsort are just like their "unstable" counterparts, except that items which compare the same get maintained in their original order. stable = loyal. πŸ’–


πŸŽ€ EXAMPLES πŸŽ€

Here's some sample data (chilling in the array @data):

123   asd   1.22   asdd
32    ewq   2.32   asdd
43    rewq  2.12   ewet
51    erwt  34.2   ewet
23    erww  4.21   ewet
91    fdgs  3.43   ewet
123   refs  3.22   asdd
123   refs  4.32   asdd

alpha sort on column 1

print fieldsort [1], @data;
123   asd   1.22   asdd
123   refs  3.22   asdd
123   refs  4.32   asdd
23    erww  4.21   ewet
32    ewq   2.32   asdd
43    rewq  2.12   ewet
51    erwt  34.2   ewet
91    fdgs  3.43   ewet

numeric sort on column 1

print fieldsort ['1n'], @data;
23    erww  4.21   ewet
32    ewq   2.32   asdd
43    rewq  2.12   ewet
51    erwt  34.2   ewet
91    fdgs  3.43   ewet
123   asd   1.22   asdd
123   refs  3.22   asdd
123   refs  4.32   asdd

reverse numeric sort on column 1

print fieldsort ['-1n'], @data;
123   asd   1.22   asdd
123   refs  3.22   asdd
123   refs  4.32   asdd
91    fdgs  3.43   ewet
51    erwt  34.2   ewet
43    rewq  2.12   ewet
32    ewq   2.32   asdd
23    erww  4.21   ewet

alpha sort on column 2, then alpha on entire line

print fieldsort [2, 0], @data;
123   asd   1.22   asdd
51    erwt  34.2   ewet
23    erww  4.21   ewet
32    ewq   2.32   asdd
91    fdgs  3.43   ewet
123   refs  3.22   asdd
123   refs  4.32   asdd
43    rewq  2.12   ewet

alpha sort on column 4, then numeric on column 1, then reverse numeric on column 3

# alpha sort on column 4, then numeric on column 1, then reverse
# numeric on column 3
print fieldsort [4, '1n', '-3n'], @data;
32    ewq   2.32   asdd
123   refs  4.32   asdd
123   refs  3.22   asdd
123   asd   1.22   asdd
23    erww  4.21   ewet
43    rewq  2.12   ewet
51    erwt  34.2   ewet
91    fdgs  3.43   ewet

splitting on either literal period or whitespace

now we split on either literal period or whitespace, sort numeric on column 4 (the fractional part of the decimals) then numeric on column 3 (the whole part of the decimals):

# now, splitting on either literal period or whitespace
# sort numeric on column 4 (fractional part of decimals) then
# numeric on column 3 (whole part of decimals)
print fieldsort '(?:\.|\s+)', ['4n', '3n'], @data;
51    erwt  34.2   ewet
43    rewq  2.12   ewet
23    erww  4.21   ewet
123   asd   1.22   asdd
123   refs  3.22   asdd
32    ewq   2.32   asdd
123   refs  4.32   asdd
91    fdgs  3.43   ewet

alpha sort on column 4, then numeric on the entire line

🚨 NOTE: this one produces warnings under -w. you have been warned, bestie.
# alpha sort on column 4, then numeric on the entire line
# NOTE: produces warnings under -w
print fieldsort [4, '0n'], @data;
32    ewq   2.32   asdd
123   asd   1.22   asdd
123   refs  3.22   asdd
123   refs  4.32   asdd
23    erww  4.21   ewet
43    rewq  2.12   ewet
51    erwt  34.2   ewet
91    fdgs  3.43   ewet

stable alpha sort on column 4

(this one maintains the original relative order among items that compare the same πŸ₯Ί)

# stable alpha sort on column 4 (maintains original relative order
# among items that compare the same)
print stable_fieldsort [4], @data;
123   asd   1.22   asdd
32    ewq   2.32   asdd
123   refs  3.22   asdd
123   refs  4.32   asdd
43    rewq  2.12   ewet
51    erwt  34.2   ewet
23    erww  4.21   ewet
91    fdgs  3.43   ewet

πŸ™ˆ BUGS πŸ™ˆ

Some rudimentary tests now. (yeah. that's the whole sentence. iconic.)

Perhaps something should be done to catch things like:

fieldsort '.', [1, 2], @lines;

Because '.' translates to split /./ β€” which is probably not what you want. 😭

Also: passing blank lines and/or lines containing the wrong kind of data (alphas instead of numbers) can result in copious warning messages under -w. like, a lot of them. brace yourself. πŸ’€

And if the regexp contains memory parentheses ((...) rather than (?:...)), split will function in "delimiter retention" mode, capturing the contents of the parentheses as well as the stuff between the delimiters. The author could imagine how this could be useful β€” but on the other hand, could also imagine how it could be confusing if you encountered it unexpectedly. Caveat sortor. 🧚

Not really a bug, but if you're planning to sort a large text file, consider using sort(1) instead. Unless, of course, your operating system doesn't have sort(1). in which case... well. 🫠


πŸ‘‘ AUTHOR πŸ‘‘

Joseph N. Hall, <joseph@5sigma.com>


🌈 SEE ALSO 🌈


and that's the whole page bestie!! this is perl v5.40.1, dated 2025-04-17 β€” go forth and sort your fields, you absolute legend. mwah. πŸ’–βœ¨πŸŽ€πŸ¦‹πŸŒΈπŸ’…πŸ«Ά

πŸ“¦ where this page comes from