Skip to content

Commit

Permalink
Merge branch 'develop'
Browse files Browse the repository at this point in the history
* develop:
  specify next release
  ban the use of "yield from" and iterator_to_array()
  simplify lazy Sequence::slice() implementation
  remove dead code
  mention the callable passed to reduce may not be called
  fix psalm errors
  prevent loading the whole Set/Sequence/Map when matches find an invalid value
  fix psalm error
  fix loading the whole the Generator when lazy slicing a Sequence
  • Loading branch information
Baptouuuu committed May 18, 2023
2 parents a15d1e4 + 7418a58 commit 5b85b79
Show file tree
Hide file tree
Showing 21 changed files with 242 additions and 133 deletions.
12 changes: 12 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,17 @@
# Changelog

## 4.14.1 - 2023-05-18

### Changed

- All `reduce` methods now explicit the fact that the callable may not be called when the structure is empty

### Fixed

- A lazy `Sequence::slice()` no longer loads the whole underlying `Generator`
- `Innmind\Immutable\Set::matches()`, `Innmind\Immutable\Sequence::matches()` and `Innmind\Immutable\Map::matches()` no longer iterates over all elements when one value doesn't match the predicate
- When using `yield from` in the `Generator` passed to `Sequence::lazy()` values may be lost on certain operations

## 4.14.0 - 2023-04-29

### Added
Expand Down
25 changes: 16 additions & 9 deletions src/Map.php
Original file line number Diff line number Diff line change
Expand Up @@ -224,12 +224,15 @@ public function map(callable $function): self
*/
public function flatMap(callable $map): self
{
/** @var self<A, B> */
$all = self::of();

/**
* @psalm-suppress InvalidArgument
* @psalm-suppress MixedArgument
*/
return $this->reduce(
self::of(),
$all,
static fn(self $carry, $key, $value) => $carry->merge($map($key, $value)),
);
}
Expand Down Expand Up @@ -273,11 +276,13 @@ public function partition(callable $predicate): self
/**
* Reduce the map to a single value
*
* @template I
* @template R
* @param R $carry
* @param callable(R, T, S): R $reducer
*
* @return R
* @param I $carry
* @param callable(I|R, T, S): R $reducer
*
* @return I|R
*/
public function reduce($carry, callable $reducer)
{
Expand All @@ -304,11 +309,13 @@ public function find(callable $predicate): Maybe
*/
public function matches(callable $predicate): bool
{
/** @psalm-suppress MixedArgument */
return $this->reduce(
true,
static fn(bool $matches, $key, $value): bool => $matches && $predicate($key, $value),
);
/** @psalm-suppress MixedArgument For some reason Psalm no longer recognize the type in `find` */
return $this
->find(static fn($key, $value) => !$predicate($key, $value))
->match(
static fn() => false,
static fn() => true,
);
}

/**
Expand Down
9 changes: 5 additions & 4 deletions src/Map/DoubleIndex.php
Original file line number Diff line number Diff line change
Expand Up @@ -241,7 +241,6 @@ public function remove($key): self
*/
public function merge(Implementation $map): self
{
/** @psalm-suppress MixedArgument For some reason it no longer recognize templates for $key and $value */
return $map->reduce(
$this,
static fn(self $carry, $key, $value): self => ($carry)($key, $value),
Expand Down Expand Up @@ -276,11 +275,13 @@ public function partition(callable $predicate): Map
}

/**
* @template I
* @template R
* @param R $carry
* @param callable(R, T, S): R $reducer
*
* @return R
* @param I $carry
* @param callable(I|R, T, S): R $reducer
*
* @return I|R
*/
public function reduce($carry, callable $reducer)
{
Expand Down
8 changes: 5 additions & 3 deletions src/Map/Implementation.php
Original file line number Diff line number Diff line change
Expand Up @@ -149,11 +149,13 @@ public function partition(callable $predicate): Map;
/**
* Reduce the map to a single value
*
* @template I
* @template R
* @param R $carry
* @param callable(R, T, S): R $reducer
*
* @return R
* @param I $carry
* @param callable(I|R, T, S): R $reducer
*
* @return I|R
*/
public function reduce($carry, callable $reducer);

Expand Down
18 changes: 13 additions & 5 deletions src/Map/ObjectKeys.php
Original file line number Diff line number Diff line change
Expand Up @@ -250,8 +250,11 @@ public function groupBy(callable $discriminator): Map
*/
public function keys(): Set
{
/** @var Set<T> */
$keys = Set::of();

return $this->reduce(
Set::of(),
$keys,
static fn(Set $keys, $key): Set => ($keys)($key),
);
}
Expand All @@ -261,8 +264,11 @@ public function keys(): Set
*/
public function values(): Sequence
{
/** @var Sequence<S> */
$values = Sequence::of();

return $this->reduce(
Sequence::of(),
$values,
static fn(Sequence $values, $_, $value): Sequence => ($values)($value),
);
}
Expand Down Expand Up @@ -367,11 +373,13 @@ public function partition(callable $predicate): Map
}

/**
* @template I
* @template R
* @param R $carry
* @param callable(R, T, S): R $reducer
*
* @return R
* @param I $carry
* @param callable(I|R, T, S): R $reducer
*
* @return I|R
*/
public function reduce($carry, callable $reducer)
{
Expand Down
8 changes: 5 additions & 3 deletions src/Map/Primitive.php
Original file line number Diff line number Diff line change
Expand Up @@ -308,11 +308,13 @@ public function partition(callable $predicate): Map
}

/**
* @template I
* @template R
* @param R $carry
* @param callable(R, T, S): R $reducer
*
* @return R
* @param I $carry
* @param callable(I|R, T, S): R $reducer
*
* @return I|R
*/
public function reduce($carry, callable $reducer)
{
Expand Down
8 changes: 5 additions & 3 deletions src/Map/Uninitialized.php
Original file line number Diff line number Diff line change
Expand Up @@ -190,11 +190,13 @@ public function partition(callable $predicate): Map
}

/**
* @template I
* @template R
* @param R $carry
* @param callable(R, T, S): R $reducer
*
* @return R
* @param I $carry
* @param callable(I|R, T, S): R $reducer
*
* @return I|R
*/
public function reduce($carry, callable $reducer)
{
Expand Down
4 changes: 3 additions & 1 deletion src/Maybe/Defer.php
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,9 @@ public function toSequence(): Sequence
{
/** @psalm-suppress ImpureFunctionCall */
return Sequence::defer((function() {
yield from $this->unwrap()->toSequence()->toList();
foreach ($this->unwrap()->toSequence()->toList() as $value) {
yield $value;
}
})());
}

Expand Down
35 changes: 18 additions & 17 deletions src/Sequence.php
Original file line number Diff line number Diff line change
Expand Up @@ -536,10 +536,7 @@ public function sort(callable $function): self
*/
public function fold(Monoid $monoid)
{
/**
* @psalm-suppress MissingClosureParamType
* @psalm-suppress MixedArgument
*/
/** @psalm-suppress MixedArgument */
return $this->reduce(
$monoid->identity(),
static fn($a, $b) => $monoid->combine($a, $b),
Expand All @@ -549,12 +546,13 @@ public function fold(Monoid $monoid)
/**
* Reduce the sequence to a single value
*
* @template I
* @template R
*
* @param R $carry
* @param callable(R, T): R $reducer
* @param I $carry
* @param callable(I|R, T): R $reducer
*
* @return R
* @return I|R
*/
public function reduce($carry, callable $reducer)
{
Expand Down Expand Up @@ -599,13 +597,14 @@ public function toSet(): Set
*/
public function toList(): array
{
/**
* @psalm-suppress MixedAssignment
* @var list<T>
*/
/** @var list<T> */
$all = [];

/** @var list<T> */
return $this->reduce(
[],
$all,
static function(array $carry, $value): array {
/** @var T $value */
$carry[] = $value;

return $carry;
Expand Down Expand Up @@ -645,11 +644,13 @@ public function match(callable $match, callable $empty)
*/
public function matches(callable $predicate): bool
{
/** @psalm-suppress MixedArgument */
return $this->reduce(
true,
static fn(bool $matches, $value): bool => $matches && $predicate($value),
);
/** @psalm-suppress MixedArgument For some reason Psalm no longer recognize the type in `find` */
return $this
->find(static fn($value) => !$predicate($value))
->match(
static fn() => false,
static fn() => true,
);
}

/**
Expand Down
40 changes: 29 additions & 11 deletions src/Sequence/Defer.php
Original file line number Diff line number Diff line change
Expand Up @@ -507,24 +507,30 @@ public function sort(callable $function): Implementation
(static function(\Iterator $values, callable $function): \Generator {
/** @var callable(T, T): int $sorter */
$sorter = $function;
$loaded = [];

/** @var list<T> */
$values = \iterator_to_array($values);
\usort($values, $sorter);

/** @var T $value */
foreach ($values as $value) {
$loaded[] = $value;
}

\usort($loaded, $sorter);

foreach ($loaded as $value) {
yield $value;
}
})($this->values, $function),
);
}

/**
* @template I
* @template R
* @param R $carry
* @param callable(R, T): R $reducer
*
* @return R
* @param I $carry
* @param callable(I|R, T): R $reducer
*
* @return I|R
*/
public function reduce($carry, callable $reducer)
{
Expand Down Expand Up @@ -552,9 +558,16 @@ public function reverse(): Implementation
/** @psalm-suppress ImpureFunctionCall */
return new self(
(static function(\Iterator $values): \Generator {
$values = \iterator_to_array($values);
$reversed = [];

yield from \array_reverse($values);
/** @var T $value */
foreach ($values as $value) {
\array_unshift($reversed, $value);
}

foreach ($reversed as $value) {
yield $value;
}
})($this->values),
);
}
Expand Down Expand Up @@ -766,7 +779,12 @@ public function takeWhile(callable $condition): self
*/
private function load(): Implementation
{
/** @psalm-suppress ImpureFunctionCall */
return new Primitive(\array_values(\iterator_to_array($this->values)));
$values = [];

foreach ($this->values as $value) {
$values[] = $value;
}

return new Primitive($values);
}
}
8 changes: 5 additions & 3 deletions src/Sequence/Implementation.php
Original file line number Diff line number Diff line change
Expand Up @@ -251,11 +251,13 @@ public function sort(callable $function): self;
/**
* Reduce the sequence to a single value
*
* @template I
* @template R
* @param R $carry
* @param callable(R, T): R $reducer
*
* @return R
* @param I $carry
* @param callable(I|R, T): R $reducer
*
* @return I|R
*/
public function reduce($carry, callable $reducer);

Expand Down
Loading

0 comments on commit 5b85b79

Please sign in to comment.