123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268 |
- --TEST--
- foreach with iteratorAggregate
- --FILE--
- <?php
- class EnglishMealIterator implements Iterator {
- private $pos=0;
- private $myContent=array("breakfast", "dinner", "tea");
- public function valid(): bool {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- return $this->pos < count($this->myContent);
- }
- public function next(): void {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- $this->pos++;
- }
- public function rewind(): void {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- $this->pos=0;
- }
- public function current(): mixed {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- return $this->myContent[$this->pos];
- }
- public function key(): mixed {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- return "meal " . $this->pos;
- }
- }
- class FrenchMealIterator implements Iterator {
- private $pos=0;
- private $myContent=array("petit dejeuner", "dejeuner", "gouter", "dinner");
- public function valid(): bool {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- return $this->pos < count($this->myContent);
- }
- public function next(): void {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- $this->pos++;
- }
- public function rewind(): void {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- $this->pos=0;
- }
- public function current(): mixed {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- return $this->myContent[$this->pos];
- }
- public function key(): mixed {
- global $indent;
- echo "$indent--> " . __METHOD__ . " ($this->pos)\n";
- return "meal " . $this->pos;
- }
- }
- Class EuropeanMeals implements IteratorAggregate {
- private $storedEnglishMealIterator;
- private $storedFrenchMealIterator;
- public function __construct() {
- $this->storedEnglishMealIterator = new EnglishMealIterator;
- $this->storedFrenchMealIterator = new FrenchMealIterator;
- }
- public function getIterator(): Traversable {
- global $indent;
- echo "$indent--> " . __METHOD__ . "\n";
- //Alternate between English and French meals
- static $i = 0;
- if ($i++%2 == 0) {
- return $this->storedEnglishMealIterator;
- } else {
- return $this->storedFrenchMealIterator;
- }
- }
- }
- $f = new EuropeanMeals;
- var_dump($f);
- echo "-----( Simple iteration 1: )-----\n";
- foreach ($f as $k=>$v) {
- echo "$k => $v\n";
- }
- echo "-----( Simple iteration 2: )-----\n";
- foreach ($f as $k=>$v) {
- echo "$k => $v\n";
- }
- $indent = " ";
- echo "\n\n\n-----( Nested iteration: )-----\n";
- $count=1;
- foreach ($f as $k=>$v) {
- echo "\nTop level " . $count++ . ": \n";
- echo "$k => $v\n";
- $indent = " ";
- foreach ($f as $k=>$v) {
- echo " $k => $v\n";
- }
- $indent = " ";
- }
- ?>
- --EXPECTF--
- object(EuropeanMeals)#%d (2) {
- ["storedEnglishMealIterator":"EuropeanMeals":private]=>
- object(EnglishMealIterator)#%d (2) {
- ["pos":"EnglishMealIterator":private]=>
- int(0)
- ["myContent":"EnglishMealIterator":private]=>
- array(3) {
- [0]=>
- string(9) "breakfast"
- [1]=>
- string(6) "dinner"
- [2]=>
- string(3) "tea"
- }
- }
- ["storedFrenchMealIterator":"EuropeanMeals":private]=>
- object(FrenchMealIterator)#%d (2) {
- ["pos":"FrenchMealIterator":private]=>
- int(0)
- ["myContent":"FrenchMealIterator":private]=>
- array(4) {
- [0]=>
- string(14) "petit dejeuner"
- [1]=>
- string(8) "dejeuner"
- [2]=>
- string(6) "gouter"
- [3]=>
- string(6) "dinner"
- }
- }
- }
- -----( Simple iteration 1: )-----
- --> EuropeanMeals::getIterator
- --> EnglishMealIterator::rewind (0)
- --> EnglishMealIterator::valid (0)
- --> EnglishMealIterator::current (0)
- --> EnglishMealIterator::key (0)
- meal 0 => breakfast
- --> EnglishMealIterator::next (0)
- --> EnglishMealIterator::valid (1)
- --> EnglishMealIterator::current (1)
- --> EnglishMealIterator::key (1)
- meal 1 => dinner
- --> EnglishMealIterator::next (1)
- --> EnglishMealIterator::valid (2)
- --> EnglishMealIterator::current (2)
- --> EnglishMealIterator::key (2)
- meal 2 => tea
- --> EnglishMealIterator::next (2)
- --> EnglishMealIterator::valid (3)
- -----( Simple iteration 2: )-----
- --> EuropeanMeals::getIterator
- --> FrenchMealIterator::rewind (0)
- --> FrenchMealIterator::valid (0)
- --> FrenchMealIterator::current (0)
- --> FrenchMealIterator::key (0)
- meal 0 => petit dejeuner
- --> FrenchMealIterator::next (0)
- --> FrenchMealIterator::valid (1)
- --> FrenchMealIterator::current (1)
- --> FrenchMealIterator::key (1)
- meal 1 => dejeuner
- --> FrenchMealIterator::next (1)
- --> FrenchMealIterator::valid (2)
- --> FrenchMealIterator::current (2)
- --> FrenchMealIterator::key (2)
- meal 2 => gouter
- --> FrenchMealIterator::next (2)
- --> FrenchMealIterator::valid (3)
- --> FrenchMealIterator::current (3)
- --> FrenchMealIterator::key (3)
- meal 3 => dinner
- --> FrenchMealIterator::next (3)
- --> FrenchMealIterator::valid (4)
- -----( Nested iteration: )-----
- --> EuropeanMeals::getIterator
- --> EnglishMealIterator::rewind (3)
- --> EnglishMealIterator::valid (0)
- --> EnglishMealIterator::current (0)
- --> EnglishMealIterator::key (0)
- Top level 1:
- meal 0 => breakfast
- --> EuropeanMeals::getIterator
- --> FrenchMealIterator::rewind (4)
- --> FrenchMealIterator::valid (0)
- --> FrenchMealIterator::current (0)
- --> FrenchMealIterator::key (0)
- meal 0 => petit dejeuner
- --> FrenchMealIterator::next (0)
- --> FrenchMealIterator::valid (1)
- --> FrenchMealIterator::current (1)
- --> FrenchMealIterator::key (1)
- meal 1 => dejeuner
- --> FrenchMealIterator::next (1)
- --> FrenchMealIterator::valid (2)
- --> FrenchMealIterator::current (2)
- --> FrenchMealIterator::key (2)
- meal 2 => gouter
- --> FrenchMealIterator::next (2)
- --> FrenchMealIterator::valid (3)
- --> FrenchMealIterator::current (3)
- --> FrenchMealIterator::key (3)
- meal 3 => dinner
- --> FrenchMealIterator::next (3)
- --> FrenchMealIterator::valid (4)
- --> EnglishMealIterator::next (0)
- --> EnglishMealIterator::valid (1)
- --> EnglishMealIterator::current (1)
- --> EnglishMealIterator::key (1)
- Top level 2:
- meal 1 => dinner
- --> EuropeanMeals::getIterator
- --> EnglishMealIterator::rewind (1)
- --> EnglishMealIterator::valid (0)
- --> EnglishMealIterator::current (0)
- --> EnglishMealIterator::key (0)
- meal 0 => breakfast
- --> EnglishMealIterator::next (0)
- --> EnglishMealIterator::valid (1)
- --> EnglishMealIterator::current (1)
- --> EnglishMealIterator::key (1)
- meal 1 => dinner
- --> EnglishMealIterator::next (1)
- --> EnglishMealIterator::valid (2)
- --> EnglishMealIterator::current (2)
- --> EnglishMealIterator::key (2)
- meal 2 => tea
- --> EnglishMealIterator::next (2)
- --> EnglishMealIterator::valid (3)
- --> EnglishMealIterator::next (3)
- --> EnglishMealIterator::valid (4)
|