使用 PHP - SPL 解决方案反向迭代数组?

发布于 2024-10-22 05:51:50 字数 268 浏览 6 评论 0原文

PHP 中有 SPL 反向数组迭代器吗? 如果没有,实现这一目标的最佳方法是什么?

我可以简单地做

$array = array_reverse($array);
foreach($array as $currentElement) {}

或者

for($i = count($array) - 1; $i >= 0; $i--)
{

}

但是有更优雅的方法吗?

Is there an SPL Reverse array iterator in PHP?
And if not, what would be the best way to achieve it?

I could simply do

$array = array_reverse($array);
foreach($array as $currentElement) {}

or

for($i = count($array) - 1; $i >= 0; $i--)
{

}

But is there a more elegant way?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(11

花落人断肠 2024-10-29 05:51:50

这是一个不复制也不修改数组的解决方案:

for ($currentElement = end($array); key($array) !== null; $currentElement = prev($array)) {
  // ...
}

如果您还想要对当前键的引用:

for ($currentElement = end($array); ($currentKey = key($array)) !== null; $currentElement = prev($array)) {
  // ...
}

这始终有效,因为 php 数组键永远不会为空,并且比此处给出的任何其他答案更快。

Here is a solution that does not copy and does not modify the array:

for ($currentElement = end($array); key($array) !== null; $currentElement = prev($array)) {
  // ...
}

If you also want a reference to the current key:

for ($currentElement = end($array); ($currentKey = key($array)) !== null; $currentElement = prev($array)) {
  // ...
}

This works always as php array keys can never be null and is faster than any other answer given here.

↙厌世 2024-10-29 05:51:50
$item=end($array);
do {
...
} while ($item=prev($array));
$item=end($array);
do {
...
} while ($item=prev($array));
飘然心甜 2024-10-29 05:51:50

没有 ReverseArrayIterator 可以做到这一点。您可以将

$reverted = new ArrayIterator(array_reverse($data));

其放入您自己的自定义迭代器中,例如,

class ReverseArrayIterator extends ArrayIterator 
{
    public function __construct(array $array)
    {
        parent::__construct(array_reverse($array));
    }
}

不使用 array_reverse 但通过标准数组函数迭代数组的稍长的实现将是

class ReverseArrayIterator implements Iterator
{
    private $array;

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

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

    public function next()
    {
        return prev($this->array);
    }

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

    public function valid()
    {
        return key($this->array) !== null;
    }

    public function rewind()
    {
        end($this->array);
    }
}

There is no ReverseArrayIterator to do that. You can do

$reverted = new ArrayIterator(array_reverse($data));

or make that into your own custom iterator, e.g.

class ReverseArrayIterator extends ArrayIterator 
{
    public function __construct(array $array)
    {
        parent::__construct(array_reverse($array));
    }
}

A slightly longer implementation that doesn't use array_reverse but iterates the array via the standard array functions would be

class ReverseArrayIterator implements Iterator
{
    private $array;

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

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

    public function next()
    {
        return prev($this->array);
    }

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

    public function valid()
    {
        return key($this->array) !== null;
    }

    public function rewind()
    {
        end($this->array);
    }
}
命硬 2024-10-29 05:51:50

根据 linepogl 的答案,我想出了这个函数:

/**
 * Iterate an array or other foreach-able without making a copy of it.
 *
 * @param array|\Traversable $iterable
 * @return Generator
 */
function iter_reverse($iterable) {
    for (end($iterable); ($key=key($iterable))!==null; prev($iterable)){
        yield $key => current($iterable);
    }
}

用法:

foreach(iter_reverse($my_array) as $key => $value) {
    // ... do things ...
}

这适用于数组和其他可迭代对象,无需先进行复制它的。

Based on linepogl's answer, I came up with this function:

/**
 * Iterate an array or other foreach-able without making a copy of it.
 *
 * @param array|\Traversable $iterable
 * @return Generator
 */
function iter_reverse($iterable) {
    for (end($iterable); ($key=key($iterable))!==null; prev($iterable)){
        yield $key => current($iterable);
    }
}

Usage:

foreach(iter_reverse($my_array) as $key => $value) {
    // ... do things ...
}

This works on arrays and other iterables without first making a copy of it.

那伤。 2024-10-29 05:51:50

根据您想要执行的操作,您可能需要研究 spl 数据结构类,例如 SplStack。 SplStack 实现了 Iterator、ArrayAccess 和 Countable,因此它主要可以像数组一样使用,但默认情况下,它的迭代器按 FILO 顺序进行。例如:

$stack = new SplStack();
$stack[] = 'one';
$stack[] = 'two';
$stack[] = 'three';

foreach ($stack as $item)
{
    print "$item\n";
}

这将打印

three
two
one

Depending on what you are trying to do, you might want to look into the spl data structure classes, such as SplStack. SplStack implements Iterator, ArrayAccess and Countable, so it can mostly be used like an array, but by default, its iterator proceeds in FILO order. Ex:

$stack = new SplStack();
$stack[] = 'one';
$stack[] = 'two';
$stack[] = 'three';

foreach ($stack as $item)
{
    print "$item\n";
}

This will print

three
two
one
○闲身 2024-10-29 05:51:50

请注意,如果要保留数组的键,则必须将 true 作为第二个参数传递给 array_reverse

$array = array_reverse($array, true);
foreach ($array as $currentElement) {
    // do something here
}

Note that if you want to preserve the keys of the array, you must pass true as the second parameter to array_reverse:

$array = array_reverse($array, true);
foreach ($array as $currentElement) {
    // do something here
}
紫轩蝶泪 2024-10-29 05:51:50

基于linepogl的答案...您可以通过避免 current() 调用来提高效率

for ($value = end($array); ($key = key($array)) !== null; $value = prev($array)) {
     // ... do something with $key => $value
}

Based on linepogl's answer... You can make it even more efficient by avoiding current() call

for ($value = end($array); ($key = key($array)) !== null; $value = prev($array)) {
     // ... do something with $key => $value
}
兲鉂ぱ嘚淚 2024-10-29 05:51:50
$array = array_reverse($array);
foreach($array as $key => $currentElement) {}

这是更好的使用方法。如果键不是连续的或整数,它也会处理它们。

$array = array_reverse($array);
foreach($array as $key => $currentElement) {}

This is better way to use. It will take care of keys also, if they are not sequential or integer.

世态炎凉 2024-10-29 05:51:50
$array=array(
    0 => 0,
    '1' => 1,
    2 => null,
    3 => false
);

$value=end( $array );                      // ← value for first iteration
while(($key=key( $array )) !== null) {
  echo "key=$key, value=$value\n";

  $value=prev( $array );                   // ← value for next iteration
}
$array=array(
    0 => 0,
    '1' => 1,
    2 => null,
    3 => false
);

$value=end( $array );                      // ← value for first iteration
while(($key=key( $array )) !== null) {
  echo "key=$key, value=$value\n";

  $value=prev( $array );                   // ← value for next iteration
}
三寸金莲 2024-10-29 05:51:50

这可能是一种更高效的方法,因为它不构造新数组。它还可以很好地处理空数组。

$item = end($items);
while($item)
{
    ...do stuff...
    $item = prev($items);
}

This could be a more performant way since it doesnt construct a new array. It also handles empty arrays well.

$item = end($items);
while($item)
{
    ...do stuff...
    $item = prev($items);
}
饮惑 2024-10-29 05:51:50

$array1= 数组(10,20,30,40,50);

        for($i = count($array1) - 1; $i >= 0; $i--)
        {
            $array2[]  = $array1[$i];

        }

        echo "<pre>";
            print_r($array2);
        echo "</pre>";

$array1= array(10,20,30,40,50);

        for($i = count($array1) - 1; $i >= 0; $i--)
        {
            $array2[]  = $array1[$i];

        }

        echo "<pre>";
            print_r($array2);
        echo "</pre>";
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文