From 4257c269775d9f8b839202b225f28f2f7ce47a40 Mon Sep 17 00:00:00 2001 From: Pol Dellaiera Date: Sun, 15 Aug 2021 21:08:11 +0200 Subject: [PATCH 1/6] refactor: Update Window operation in point free style. --- spec/loophp/collection/CollectionSpec.php | 8 +++-- src/Operation/Window.php | 37 ++++++++++------------- 2 files changed, 22 insertions(+), 23 deletions(-) diff --git a/spec/loophp/collection/CollectionSpec.php b/spec/loophp/collection/CollectionSpec.php index e50f6770f..f67432775 100644 --- a/spec/loophp/collection/CollectionSpec.php +++ b/spec/loophp/collection/CollectionSpec.php @@ -3999,9 +3999,13 @@ public function it_can_when(): void public function it_can_window(): void { - $this::fromIterable(range('a', 'z')) + $this::fromIterable(range('a', 'c')) ->window(0) - ->shouldIterateAs(range('a', 'z')); + ->shouldIterateAs([ + ['a'], + ['b'], + ['c'], + ]); $this::fromIterable(range('a', 'z')) ->window(2) diff --git a/src/Operation/Window.php b/src/Operation/Window.php index ff16524b9..4a2024171 100644 --- a/src/Operation/Window.php +++ b/src/Operation/Window.php @@ -32,27 +32,22 @@ public function __invoke(): Closure { return /** - * @return Closure(Iterator): Generator> + * @return Closure(Iterator): Generator> */ - static fn (int $size): Closure => - /** - * @param Iterator $iterator - * - * @return Generator|T> - */ - static function (Iterator $iterator) use ($size): Generator { - if (0 === $size) { - return yield from $iterator; - } - - ++$size; - $size *= -1; - - $stack = []; - - foreach ($iterator as $key => $current) { - yield $key => $stack = array_slice([...$stack, $current], $size); - } - }; + static function (int $size): Closure { + /** @var Closure(Iterator): Generator> $reduction */ + $reduction = Reduction::of()( + /** + * @param list $stack + * @param T $current + * + * @return list + */ + static fn (array $stack, $current): array => array_slice([...$stack, $current], ++$size * -1) + )([]); + + // Point free style. + return $reduction; + }; } } From 7e7c937b3b42970f1ad571c9483a75233ba760a1 Mon Sep 17 00:00:00 2001 From: Pol Dellaiera Date: Thu, 19 Aug 2021 13:32:07 +0200 Subject: [PATCH 2/6] docs: Update Window operation documentation. --- docs/pages/api.rst | 12 ++++++------ docs/pages/code/operations/window.php | 28 +++++++++++++++++++++++++++ 2 files changed, 34 insertions(+), 6 deletions(-) create mode 100644 docs/pages/code/operations/window.php diff --git a/docs/pages/api.rst b/docs/pages/api.rst index 6ca3c1b92..2b65b2f06 100644 --- a/docs/pages/api.rst +++ b/docs/pages/api.rst @@ -2439,16 +2439,16 @@ window Loop the collection yielding windows of data by adding a given number of items to the current item. Initially the windows yielded will be smaller, until size ``1 + $size`` is reached. -Interface: `Windowable`_ +.. tip:: To remove the window size constraint and have a dynamic window size, set the ``$size`` to ``-1``. -Signature: ``Collection::window(int $size): Collection;`` +.. note:: When ``$size`` is equal to ``0``, the window will only contain the current element, wrapped in an array. -.. code-block:: php +Interface: `Windowable`_ - $data = range('a', 'd'); +Signature: ``Collection::window(int $size): Collection;`` - Collection::fromIterable($data) - ->window(2); // [['a'], ['a', 'b'], ['a', 'b', 'c'], ['b', 'c', 'd']] +.. literalinclude:: code/operations/window.php + :language: php words ~~~~~ diff --git a/docs/pages/code/operations/window.php b/docs/pages/code/operations/window.php new file mode 100644 index 000000000..95247692d --- /dev/null +++ b/docs/pages/code/operations/window.php @@ -0,0 +1,28 @@ +window(0); // [['a'], ['b'], ['c'], ['d'], ['e']] + +Collection::fromIterable($data) + ->window(1); // [['a'], ['a', 'b'], ['b', 'c'], ['c', 'd'], ['d', 'e']] + +Collection::fromIterable($data) + ->window(2); // [['a'], ['a', 'b'], ['a', 'b', 'c'], ['b', 'c', 'd'], ['c', 'd', 'e']] + +Collection::fromIterable($data) + ->window(-1); // [['a'], ['a', 'b'], ['a', 'b', 'c'], ['a', 'b', 'c', 'd'], ['a', 'b', 'c', 'd', 'e']] From eaf8c7cccaa7ec711dfeb6ee448f0117f7363731 Mon Sep 17 00:00:00 2001 From: Pol Dellaiera Date: Thu, 19 Aug 2021 13:32:50 +0200 Subject: [PATCH 3/6] fix: Fix SA return types. --- src/Operation/Window.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Operation/Window.php b/src/Operation/Window.php index 4a2024171..335c3513b 100644 --- a/src/Operation/Window.php +++ b/src/Operation/Window.php @@ -26,7 +26,7 @@ final class Window extends AbstractOperation /** * @pure * - * @return Closure(int): Closure(Iterator): Generator> + * @return Closure(int): Closure(Iterator): Generator> */ public function __invoke(): Closure { From b3d537902b2ef363a618bd4409a4bb8f0d0c0c04 Mon Sep 17 00:00:00 2001 From: Pol Dellaiera Date: Thu, 19 Aug 2021 13:33:04 +0200 Subject: [PATCH 4/6] fix: Fix minor typo. --- src/Contract/Operation/Windowable.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Contract/Operation/Windowable.php b/src/Contract/Operation/Windowable.php index 71f69e153..3552d477d 100644 --- a/src/Contract/Operation/Windowable.php +++ b/src/Contract/Operation/Windowable.php @@ -19,7 +19,7 @@ interface Windowable { /** * Loop the collection yielding windows of data by adding a given number of items to the current item. - * Initially the windows yielded will be smaller, until size` 1 + $size` is reached. + * Initially the windows yielded will be smaller, until size `1 + $size` is reached. * * @see https://loophp-collection.readthedocs.io/en/stable/pages/api.html#window * From 202094e2358d31c489218b268d0d9657ca46bcf9 Mon Sep 17 00:00:00 2001 From: Pol Dellaiera Date: Thu, 19 Aug 2021 13:33:30 +0200 Subject: [PATCH 5/6] tests: Add/update window operation tests. --- spec/loophp/collection/CollectionSpec.php | 122 +++------------------- 1 file changed, 12 insertions(+), 110 deletions(-) diff --git a/spec/loophp/collection/CollectionSpec.php b/spec/loophp/collection/CollectionSpec.php index ac38672e7..1ffc4311c 100644 --- a/spec/loophp/collection/CollectionSpec.php +++ b/spec/loophp/collection/CollectionSpec.php @@ -4012,15 +4012,15 @@ public function it_can_when(): void public function it_can_window(): void { - $this::fromIterable(range('a', 'c')) + $this::fromIterable(['a' => 'A', 'b' => 'B', 'c' => 'C']) ->window(0) ->shouldIterateAs([ - ['a'], - ['b'], - ['c'], + 'a' => ['A'], + 'b' => ['B'], + 'c' => ['C'], ]); - $this::fromIterable(range('a', 'z')) + $this::fromIterable(range('a', 'e')) ->window(2) ->shouldIterateAs([ 0 => [ @@ -4045,111 +4045,13 @@ public function it_can_window(): void 1 => 'd', 2 => 'e', ], - 5 => [ - 0 => 'd', - 1 => 'e', - 2 => 'f', - ], - 6 => [ - 0 => 'e', - 1 => 'f', - 2 => 'g', - ], - 7 => [ - 0 => 'f', - 1 => 'g', - 2 => 'h', - ], - 8 => [ - 0 => 'g', - 1 => 'h', - 2 => 'i', - ], - 9 => [ - 0 => 'h', - 1 => 'i', - 2 => 'j', - ], - 10 => [ - 0 => 'i', - 1 => 'j', - 2 => 'k', - ], - 11 => [ - 0 => 'j', - 1 => 'k', - 2 => 'l', - ], - 12 => [ - 0 => 'k', - 1 => 'l', - 2 => 'm', - ], - 13 => [ - 0 => 'l', - 1 => 'm', - 2 => 'n', - ], - 14 => [ - 0 => 'm', - 1 => 'n', - 2 => 'o', - ], - 15 => [ - 0 => 'n', - 1 => 'o', - 2 => 'p', - ], - 16 => [ - 0 => 'o', - 1 => 'p', - 2 => 'q', - ], - 17 => [ - 0 => 'p', - 1 => 'q', - 2 => 'r', - ], - 18 => [ - 0 => 'q', - 1 => 'r', - 2 => 's', - ], - 19 => [ - 0 => 'r', - 1 => 's', - 2 => 't', - ], - 20 => [ - 0 => 's', - 1 => 't', - 2 => 'u', - ], - 21 => [ - 0 => 't', - 1 => 'u', - 2 => 'v', - ], - 22 => [ - 0 => 'u', - 1 => 'v', - 2 => 'w', - ], - 23 => [ - 0 => 'v', - 1 => 'w', - 2 => 'x', - ], - 24 => [ - 0 => 'w', - 1 => 'x', - 2 => 'y', - ], - 25 => [ - 0 => 'x', - 1 => 'y', - 2 => 'z', - ], + ]); + + // Unsupported - but tested. + $this::fromIterable(range('a', 'e')) + ->window(-2) + ->shouldIterateAs([ + [],[],[],[],[] ]); } From 6ca681ebf2cdd76f95cba1415a64e75b4c577efc Mon Sep 17 00:00:00 2001 From: Pol Dellaiera Date: Thu, 19 Aug 2021 15:09:01 +0200 Subject: [PATCH 6/6] Autofix CS. --- docs/pages/code/operations/window.php | 8 ++++---- spec/loophp/collection/CollectionSpec.php | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/docs/pages/code/operations/window.php b/docs/pages/code/operations/window.php index 95247692d..7180219de 100644 --- a/docs/pages/code/operations/window.php +++ b/docs/pages/code/operations/window.php @@ -16,13 +16,13 @@ $data = range('a', 'e'); Collection::fromIterable($data) - ->window(0); // [['a'], ['b'], ['c'], ['d'], ['e']] + ->window(0); // [['a'], ['b'], ['c'], ['d'], ['e']] Collection::fromIterable($data) - ->window(1); // [['a'], ['a', 'b'], ['b', 'c'], ['c', 'd'], ['d', 'e']] + ->window(1); // [['a'], ['a', 'b'], ['b', 'c'], ['c', 'd'], ['d', 'e']] Collection::fromIterable($data) - ->window(2); // [['a'], ['a', 'b'], ['a', 'b', 'c'], ['b', 'c', 'd'], ['c', 'd', 'e']] + ->window(2); // [['a'], ['a', 'b'], ['a', 'b', 'c'], ['b', 'c', 'd'], ['c', 'd', 'e']] Collection::fromIterable($data) - ->window(-1); // [['a'], ['a', 'b'], ['a', 'b', 'c'], ['a', 'b', 'c', 'd'], ['a', 'b', 'c', 'd', 'e']] + ->window(-1); // [['a'], ['a', 'b'], ['a', 'b', 'c'], ['a', 'b', 'c', 'd'], ['a', 'b', 'c', 'd', 'e']] diff --git a/spec/loophp/collection/CollectionSpec.php b/spec/loophp/collection/CollectionSpec.php index 1ffc4311c..88fd9b0c3 100644 --- a/spec/loophp/collection/CollectionSpec.php +++ b/spec/loophp/collection/CollectionSpec.php @@ -4051,7 +4051,7 @@ public function it_can_window(): void $this::fromIterable(range('a', 'e')) ->window(-2) ->shouldIterateAs([ - [],[],[],[],[] + [], [], [], [], [], ]); }