Menu

#566 TIP #326: Add -group option to lsort

TIP Implementation
closed-accepted
9
2008-09-29
2008-08-29
Kieran Elby
No

This is a patch to add a "-group grpSize" option to lsort to cause
it to treat the list as consisting of groups of grpSize elements,
and to then perform the sort group-wise, keeping the elements within
each group together.

This is similar to what was requested in Feature Request 747083:

https://sourceforge.net/tracker/index.php?func=detail&aid=747083&group_id=10894&atid=360894

A more detailed explanation follows (not quite a TIP yet tho!).

As well as the code change, the patch includes a change to the man page,
but I've not included any test suite changes (are there any existing tests for lsort?).

Rationale

"Flat" name-value pair lists are ubiquitous in Tcl - consider the
output of "array get", "dict create" or the input to "foreach".

It is surprising then that there is no command to directly sort
such a list by either the name or the value elements, while
preserving the name-value mapping.

Doing so currently requires turning a name-value pair list into
a list of sublists, using the lsort -index option to sort them,
then flattening the list again, which is rather fiddly and
inefficient.

With this proposal, sorting a name-value pair list by the names is
achieved with "lsort -group 2 $myList".

Specification

A new option, "-group", taking one parameter, "grpSize" will be
added to the lsort command.

If -group is supplied, the list will be treated as consisting of
groups of grpSize elements, and the groups will be sorted by either
their first element or, if the -index option is used, by the element
within each group given by the first index passed to -index (which
is then ignored by -index).

Elements always remain in the same position within their group.

The list length must be a multiple of grpSize, which in turn must be
at least 2.

Examples

| lsort -group 2 {carrot 10 apple 50 banana 25}
returns {apple 50 banana 25 carrot 10}

| lsort -group 2 -index 1 -integer {carrot 10 apple 50 banana 25}
returns {carrot 10 banana 25 apple 50}

| lsort -group 3 -index {0 1} {{Bob Smith} 25 Audi {Jane Doe} 40 Ford}
return {{Jane Doe} 40 Ford {Bob Smith} 25 Audi}
(since Smith, which is at index 1 of element 0 of the first group comes
after Doe, which is at the same position in the next group of 3.)

Limitations

Only one element in each group can be used for comparison.

Discussion

  • Kieran Elby

    Kieran Elby - 2008-09-01

    Patch to add -group option to lsort

     
  • Kieran Elby

    Kieran Elby - 2008-09-01

    Logged In: YES
    user_id=99072
    Originator: YES

    File Added: grouping_lsort.patch

     
  • Donal K. Fellows

    • milestone: --> TIP Implementation
    • priority: 5 --> 9
     
  • Donal K. Fellows

    • summary: Add -group option to lsort --> TIP #326: Add -group option to lsort
     
  • Donal K. Fellows

    Accepted with modifications and addition of (simple) tests.

     
  • Donal K. Fellows

    • status: open --> closed-accepted