gpt4 book ai didi

PHP SPL ArrayIterator v 简单 foreach

转载 作者:塔克拉玛干 更新时间:2023-11-03 05:36:18 26 4
gpt4 key购买 nike

好的,正如标题所说:与简单的 foreach 循环相比,使用 ArrayIterator 的主要好处是什么。

我有一个用作容器的对象,它的主要职责是存储一个对象数组。

有人建议我让我的类实现 IteratorAggregate 并返回一个 ArrayIterator 和我的对象数组:像这样:

  public function getIterator()
{
return new ArrayIterator($this->_objs);
}

与简单地返回数组然后使用标准的 foreach 循环遍历它们相比,我看不出这样做有什么好处。

有人能解释一下为什么这是个好主意吗?

最佳答案

实现 ArrayAccess 的好处很简单:您可以访问整个对象或只是一个非常具体的,甚至是 private 属性作为数组。

在这个非常简单的示例中,我们使用 IteratorArrayAccess 来访问名为 $array 的特定属性。

class Foo implements \ArrayAccess, \Iterator
{
public $pointer = 0;

private $array = [
'first value',
'second value',
'third value',
];

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

public function current()
{
return $this->array[ $this->pointer ];
}

public function key()
{
return $this->pointer;
}

public function next()
{
++$this->pointer;
}

public function rewind()
{
$this->pointer = 0;
}

public function valid()
{
return isset( $this->array[ $this->position ] );
}
}

我们现在可以像遍历每个数组一样遍历它:

$foo = new Foo();
foreach ( $foo as $key => $value )
{
print "Index: {$key} - Value: {$value}".PHP_EOL;
}

如前例所示,我们需要实现所有这些方法来循环访问已经存在的数据。要实现 ArrayAccess,它允许我们实际设置值,我们必须实现另一组方法:

ArrayAccess {
abstract public boolean offsetExists ( mixed $offset )
abstract public mixed offsetGet ( mixed $offset )
abstract public void offsetSet ( mixed $offset , mixed $value )
abstract public void offsetUnset ( mixed $offset )
}

现在我们可以通过简单地使用 IteratorAggregate 完全停止编写和重复该(当前/关键/下一个/等)方法集。这将它归纳为一个单一的强制方法:getIterator()

现在我们有一个像这样的结果类:

class Bar implements \ArrayAccess, \IteratorAggregate
{
private $array = [];

public function getIterator()
{
return new ArrayIterator( $this->array );
}
}

而且我们对类 $array 属性具有完整的数组访问权限。我们可以设置和取消设置值,检查它们是否返回 isset,可以遍历它们等等。更方便。它的作用与上述所有八种方法完全相同,只是通过实现IteratorAggregate

最后一点:您可能会再执行一步并实现 Traversable。这个接口(interface)非常好,因为它允许您强制实现 IteratorIteratorAggregate,而无需明确说明实现开发人员需要使用哪一个。它只是解释了对象必须是可循环的是强制性的。

$foo = new IteratorContainerController();
$foo->addDependency( Traversable $bar );

这意味着 IteratorContainerController() 的依赖项将始终是 IteratorIteratorAggregate 实现的对象。因此,有人可以简单地将 IteratorAggregate 放入,或者,如果他/她需要更细粒度的控制或在设置变量之前对变量进行预处理,他/她可以简单地使用 Iterator.

关于PHP SPL ArrayIterator v 简单 foreach,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10790885/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com