Bug 11097 – Add version of std.algorithm.group that returns group ranges
Status
RESOLVED
Resolution
DUPLICATE
Severity
enhancement
Priority
P2
Component
phobos
Product
D
Version
D2
Platform
All
OS
All
Creation time
2013-09-22T05:58:00Z
Last change time
2013-09-22T07:17:04Z
Assigned to
nobody
Creator
peter.alexander.au
Comments
Comment #0 by peter.alexander.au — 2013-09-22T05:58:50Z
std.algorithm.group returns a range of (elem, count) tuples:
int[] arr = [ 1, 2, 2, 2, 2, 3, 4, 4, 4, 5 ];
assert(equal(group(arr), [ tuple(1, 1u), tuple(2, 4u), tuple(3, 1u),
tuple(4, 3u), tuple(5, 1u) ][]));
This is fine when the predicate is equality, but when the predicate is something else, the tuple is less useful. Here's an example of grouping strings by first character:
string[] arr = [ "Alice", "Andrew", "Ben", "Bob" ];
assert(equal(group!("a.front == b.front")(arr),
[ tuple("Alice", 2), tuple("Ben", 2) ]));
This isn't very useful because there aren't two Alice's and two Ben's. Alice and Ben are just one element from the group (btw, the documentation doesn't indicate that it is always the first element in the group that is returned).
It would be nice if there was a version of the algorithm that returned the groups themselves, working like this:
string[] arr = [ "Alice", "Andrew", "Ben", "Bob" ];
assert(equal(groups!("a.front == b.front")(arr),
[ ["Alice", "Andrew"], ["Ben", "Bob"] ]));
I have used the identifier "groups" here. I'm not bothered what it is called.
Once implemented, group may be elegantly implemented in terms of groups:
auto group(alias f, R)(R r)
{
return groups!(f)(r).map!(g => tuple(g.front, g.walkLength));
}
Comment #1 by bearophile_hugs — 2013-09-22T06:56:42Z
This good idea (that makes group more similar to the Python groupby) was discussed several times in past (even by Andrei), so I suggest you to search if this is already in Bugzilla.
Comment #2 by peter.alexander.au — 2013-09-22T07:17:04Z
*** This issue has been marked as a duplicate of issue 5968 ***