我正在使用RecursiveDirectoryIterator
和RecursiveIteratorIterator
使用如下代码构建文件列表树。我需要对列表进行排序 - 按字母顺序排列目录,或按字母顺序排列。
有谁能告诉我如何对文件列表进行排序?
$dir_iterator = new RecursiveDirectoryIterator($groupDirectory);
$iterator = new RecursiveIteratorIterator($dir_iterator, RecursiveIteratorIterator::SELF_FIRST);
foreach ($iterator as $file) {
// do stuff with $file
}
答案 0 :(得分:23)
有多个可用选项,您可以使用这些选项以某种方式对迭代器进行排序。最好的选择很大程度上取决于你想要如何操作迭代器内容,你想要从迭代器中得到什么,以及你真正想要/需要多少或多少迭代器。
方法会有所不同;利用SplHeap
(或Min
,Max
种类),SplPriorityQueue
等类(可能用于文件大小等方面)或只是将迭代器包装在类似{{1}的类中可以对自己的内容进行排序。
我将使用ArrayObject
作为示例。由于您希望按字母顺序排列SplHeap
的全部内容,因此可以使用以下内容:
RecursiveDirectoryIterator
排序顺序是按字母顺序排列的,混合文件和文件夹:
class ExampleSortedIterator extends SplHeap
{
public function __construct(Iterator $iterator)
{
foreach ($iterator as $item) {
$this->insert($item);
}
}
public function compare($b,$a)
{
return strcmp($a->getRealpath(), $b->getRealpath());
}
}
$dit = new RecursiveDirectoryIterator("./path/to/files");
$rit = new RecursiveIteratorIterator($dit);
$sit = new ExampleSortedIterator($rit);
foreach ($sit as $file) {
echo $file->getPathname() . PHP_EOL;
}
答案 1 :(得分:1)
使用Iterator本身是不可能的。我已经在某个地方看到Iterator
类的扩展,它已经进行了排序但是很难记得它有问题。
也许this question的答案有帮助,即使他们指出了迭代者?
更新:Here是您的问题的一个骗局,但有一些答案 - 诚然不是很多!
答案 2 :(得分:0)
Sönke Ruempler有一个很好的解决方案:
class SortingIterator implements IteratorAggregate
{
private $iterator = null;
public function __construct(Traversable $iterator, $callback)
{
if (!is_callable($callback)) {
throw new InvalidArgumentException('Given callback is not callable!');
}
$array = iterator_to_array($iterator);
usort($array, $callback);
$this->iterator = new ArrayIterator($array);
}
public function getIterator()
{
return $this->iterator;
}
}