2017-04-24 164 views
3

在PHP 7.1中有一个新的iterable psudo类型,它抽象出数组和Traversable对象。PHP - 迭代两次泛型迭代

假设在我的代码我有一类这样的:

class Foo 
{ 
    private $iterable; 

    public function __construct(iterable $iterable) 
    { 
     $this->iterable = $iterable; 
    } 

    public function firstMethod() 
    { 
     foreach ($this->iterable as $item) {...} 
    } 

    public function secondMethod() 
    { 
     foreach ($this->iterable as $item) {...} 
    } 
} 

能正常工作是$iterable是一个数组或Iterator,除非$iterableGenerator。在这种情况下,实际上,拨打firstMethod()然后secondMethod()将产生以下Exception: Cannot traverse an already closed generator

有没有办法避免这个问题?

回答

2

发电机不能倒带。如果你想避免这个问题,你必须建立一个新的发电机。这可以,如果你创建一个实现IteratorAggregate对象可以自动完成:

class Iter implements IteratorAggregate 
{ 
    public function getIterator() 
    { 
     foreach ([1, 2, 3, 4, 5] as $i) { 
      yield $i; 
     } 
    } 
} 

然后,只需通过这个对象作为你的迭代器的实例:

$iter = new Iter(); 
$foo = new Foo($iter); 
$foo->firstMethod(); 
$foo->secondMethod(); 

输出:

1 
2 
3 
4 
5 
1 
2 
3 
4 
5