Re: [RFC] [Discussion] Add new function `array_group`

From: Date: Wed, 31 May 2023 00:09:36 +0000
Subject: Re: [RFC] [Discussion] Add new function `array_group`
References: 1 2 3 4 5 6 7 8  Groups: php.internals 
Request: Send a blank email to internals+get-120481@lists.php.net to get a copy of this message
> On 30.5.2023, at 21:56, Andreas Hennings <andreas@dqxtech.net> wrote: > > On Tue, 30 May 2023 at 19:25, Boro Sitnikovski <buritomath@gmail.com> wrote: >> >> Here's some more examples: >> >> 1. Use array_group to create list of singleton list: >> ``` >> $groups = array_group( $arr, function( $p1, $p2 ) { >> return false; >> } ); >> ``` >> >> (This can also be achieved with array_map returning >> [ $x ]) >> >> 2. Distinct groups for consecutive positive and negative elements >> >> ``` >> $arr = [-1,2,-3,-4,2,1,2,-3,1,1,2]; >> >> $groups = array_group( $arr, function( $p1, $p2 ) { >> return ($p1 > 0) == ($p2 > 0); >> } ); >> ``` >> >> This produces [[-1],[2],[-3,-4],[2,1,2],[-3],[1,1,2]], so >> we can easily capture the groups of highs/lows for example. >> >> 3. Group sentences (similar to explode, but still >> different) >> >> ``` >> $arr = "Hello, PHP. Good to see you."; >> $groups = array_group( str_split( $arr ), function( $p1, $p2 ) { >> return '.' !== $p1; >> } ); >> >> $groups = array_map( 'join', $groups ); >> ``` >> >> Producing [ "Hello, PHP.", " Good to see you." >> ]. >> >> 4. Grouping book sections >> ``` >> $book_sections = [ '1.0', '1.1', '1.2', '2.0', >> '2.1', '3.0', '3.1' ]; >> $groups = array_group( $book_sections, function( $p1, $p2 ) { >> return $p1[0] === $p2[0]; >> } ); >> ``` >> >> Producing [ [ '1.0', '1.1', '1.2' ], [ >> '2.0', '2.1'], [ '3.0', '3.1' ] ] >> >> and so on... >> >> Basically, it's a very general utility :) >> >> Best, >> >> Boro > > Only one of these examples actually uses a comparison function that > actually compares two adjacent values. > All the others look at a single value only, or they don't care about > the original order at all. > > And that example (2) seems quite artificial and rare. > >> so we can easily capture the groups of highs/lows for example > > How often does this problem come up in practice? > > I did actually have a look at the Haskell doc page you linked. > > https://hackage.haskell.org/package/groupBy-0.1.0.0/docs/Data-List-GroupBy..htmlÜÁØa.îÍV > zè<€9 > I wonder where this is used in the Haskell world, and how often they > need this true comparison of adjacent values. > The examples from the doc page are quite artificial. That's ok for a > doc page, but does not make a good argument for why we need it. Thanks for digging deeper in trying to understand the value that this would bring. For a more realistic example, check the following gist: https://gist.github.com/bor0/b5f449bfe85440d96abd933b9f03b310#file-test_datetime_group-php. This was a very recent thing I worked on in production. The events came ordered from the database. But also, this is not the first time I was in need of a grouping functionality. Sorry for repeating, but I see it as a handy utility. We can bring the same argument for any of the array_* functions because most of them can be implemented with for loops. If the main concern is the consecutive processing of the elements, we could add a third argument to array_group (flag) that would allow users to alter the processing behaviour - at a price, consecutive taking O(n) vs all elements taking something close to O(n^2)

« previous php.internals (#120481) next »