[php-src] Issue #15375: Generator with double enclosed `yield from` and `valid` call will skip items
| From: | malofan | Date: | Tue, 13 Aug 2024 08:10:10 +0000 |
| Subject: | [php-src] Issue #15375: Generator with double enclosed `yield from` and `valid` call will skip items | ||
| Groups: | php.bugs | ||
| Request: | Send a blank email to php-bugs+get-247485@lists.php.net to get a copy of this message | ||
Issue: https://github.com/php/php-src/issues/15375
Author: malofan
### Description
The following code:
```php
<?php
function arrayProvider()
{
yield [
'one',
'two',
'three',
];
yield [
'four',
'five',
'six',
];
yield [
'seven',
'eight',
'nine',
];
}
function iterateValues(array $array)
{
foreach ($array as $value) {
yield $value;
}
}
function g1() {
foreach (arrayProvider() as $array) {
$iterator = iterateValues($array);
if ($iterator?->valid()) {
yield from $iterator;
}
}
}
function g2() {
yield from g1();
}
foreach (g2() as $s) {
echo $s . PHP_EOL;
}
```
Resulted in this output:
```
one
two
three
five
six
eight
nine
```
But I expected this output instead:
```
one
two
three
four
five
six
seven
eight
nine
```
https://3v4l.org/GdcNh
So if we in
g2 we'll try to yield from generator g1()
AND in g1 we'll try to yield from generator
iterateValues() BUT will call valid for it before then this
valid call will move pointer to next element of generator.
It replicates ONLY with yield from -> yield from combination AND
valid call inside.
Removing valid call or one yield from, as well as replacing yield
from generator iterateValues() to foreach: yield will solve the
problem.
Also in test done by @lifinsky were found that following code in g1:
```php
$iterator->next();
yield from $iterator;
```
Resulted in this output:
```
two
three
six
nine
```
When expected:
```
two
three
five
six
eight
nine
```
https://3v4l.org/Aq6NF
So next call also jumps and results in missed values.
### PHP Version
7.0.0 - 7.0.33, 7.1.0 - 7.1.33, 7.2.0 - 7.2.34, 7.3.0 - 7.3.33, 7.4.0 - 7.4.33, 8.0.0 - 8.0.30,
8.1.0 - 8.1.29, 8.2.0 - 8.2.22, 8.3.0 - 8.3.10
### Operating System
_No response_