Итераторы, коллекции и PHP

T. Anre

Новичок
Итераторы, коллекции и PHP

PHP:
<?php
// Интерфейс коллекции
interface ICollection
{
	public function equals(Collection $c);

	public function toArray();

	public function add($item);

	public function addAll(Collection $c);

	public function containsAll(Collection $c);

	public function retainAll(Collection $c);

	public function removeAll(Collection $c);

	public function clear();

	public function contains($item);

	public function isEmpty();

	public function Iterator();

	public function remove($item);

	public function size();

}
?>
PHP:
<?php
// Интерфейс итератора
interface IListIterator
{
	/**
	 * Добавление новго элемента
	 * @param mixed $item Элемент
	 * @return boolean
	 */
	public function add($item);

	/**
	 * Есть ли следующий элемент
	 * @return boolean
	 */
	public function hasNext();

	/**
	 * Есть ли предыдущий элемент
	 * @return boolean
	 */
	public function hasPrevious();

	/**
	 * Получить "следующий" объект
	 * @return boolean
	 */
	public function next();

	/**
	 * Получить порядковый номер следующиего элемента
	 * @return boolean
	 */
	public function nextIndex();

	/**
	 * Получить "предыдущий" объект
	 * @return boolean
	 */
	public function previous();

	/**
	 * Получить порядковый номер предыдущего элемента
	 * @return boolean
	 */
	public function previousIndex();

	/**
	 * Заменить текущий элемент другим
	 * @return boolean
	 */
	public function set($item);

	/**
	 * Удалить текущий элемент
	 * @param mixed $item Элемент
	 * @return boolean
	 */
	public function remove();

}
?>
PHP:
<?php
// Пример 1
// Код на основе коллекций и итераторов
$C = new Collection();

$C->add(new A());
$C->add(new B());

$CItr = $C->Iterator();

while ($CItr->hasNext())
	echo $CItr->next() . "\n<br/>";
PHP:
// Пример 2
// Код на базе массиовов
$C = array();

$C[] = new A();
$C[] = new B();

foreach ($C AS $Item)
	echo $Item . "\n<br/>";

?>
Как вы думаете насколько оправдано использование "связки" Коллекция-Итератор в PHP?
 

HraKK

Мудак
Команда форума
не очень. Производительность и так хромает.
 

Krishna

Продался Java
С итераторами так же можно работать через foreach.
А так ООП рулит )
Коллекции прежде всего полезны инициализацией по обращению.
 

T. Anre

Новичок
Автор оригинала: ran
Можете привести пример неразумного использования итераторов?
PHP:
<?php
$Itr = new Iterator();
$Itr->add(new ExampleClass());
while ($Itr->hasNext())
    $Itr->add(new ExampleClass());
?>
:D
 

ran

Новичок
Автор оригинала: T. Anre
PHP:
<?php
$Itr = new Iterator();
$Itr->add(new ExampleClass());
while ($Itr->hasNext())
    $Itr->add(new ExampleClass());
?>
:D
Этот код вообще завершится? ;)
Такую же ситуацию можна получить используя массивы
PHP:
<?php
$x = array();
$x[] = 'a';
reset($x);
do{
	$x[] = 'a';
}
while(next($x));
?>
Меня интересовал прежде всего случай "неразумного" использования итераторов в реальной жизни, а не бесконечный цикл, и почему хромает производительность, если итератор - это объект для обращения к элементам какой-то последовательности.

нужны ли вообще функции изменения коллекции объекту итератора? если ICollection имеет функцию contains($item) (наверное проверка существования элемента по ключу), то как добавить элемент с требуемым ключом?
 

T. Anre

Новичок
Автор оригинала: ran
Этот код вообще завершится? ;)
Когда таймаут истечет :D

Автор оригинала: ran
нужны ли вообще функции изменения коллекции объекту итератора? если ICollection имеет функцию contains($item) (наверное проверка существования элемента по ключу), то как добавить элемент с требуемым ключом?
contains($item) - проверяет, есть ли $item в коллекции, где $item - не ключ, а сам объект.
 

ran

Новичок
contains($item) - проверяет, есть ли $item в коллекции, где $item - не ключ, а сам объект.

И как такую коллекцию можно использовать? у меня есть 10 объектов юзер, о которых коллекция ничего не знает. как мне проверить, есть ли юзер в коллекции? :)
 

T. Anre

Новичок
Автор оригинала: ran
И как такую коллекцию можно использовать?
Я использую коллекции для того, чтобы набросать туда однотипные объекты, например, DOMElement'ы далее через итератор добавляю эти элементы к основному дереву. На практике - удобно.
Автор оригинала: ran
у меня есть 10 объектов юзер, о которых коллекция ничего не знает. как мне проверить, есть ли юзер в коллекции? :)
PHP:
if ($c->contains($User5))
    echo 'Юзер5 есть в коллекции';
Кстати, может не стоит использовать общий интерфейс коллекций для таких задач?
 

ran

Новичок
Автор оригинала: T. Anre
PHP:
if ($c->contains($User5))
    echo 'Юзер5 есть в коллекции';
а как коллекция узнает, что это тот юзер? что и с чем будет сравниваться?
Кстати, может не стоит использовать общий интерфейс коллекций для таких задач?
не знаю, что имеется в виду под общими задачами, но если грамотно написать 4 коллекции: map, list, queue и stack и итераторы к ним, то они подойдут для любых задач, где нужно хранить последовательности.
 

dark-demon

d(^-^)b
ну, я опять со своими глупостями :) а чем итераторы лучше обычного массива? (кроме красивых выделяющихся стрелочек...)
 

T. Anre

Новичок
Автор оригинала: ran
а как коллекция узнает, что это тот юзер? что и с чем будет сравниваться?
Коллекция просто проверяет есть ли в ней объект юзер5 и все.
 

Wicked

Новичок
dark-demon
1) Валидация значений при добавлении элементов в коллекцию. Так что потом не нужны лишние проверки: у нас в коллекции гарантированно присутствуют объекты ожидаемых классов. Массив же могут подменить или испортить, в том числе случайно.

2) возможность инкапсуляции в коллекциях функциональности, свойственной коллекциям (фильтрация, сортировка, агрегатные функции, и т.д.)

3) Более простая реализация отложенных вычислений.
 

crocodile2u

http://vbolshov.org.ru
не, знаю, может, это и не в тему, но все же:
http://www.php.net/~helly/php/ext/spl/classSplObjectStorage.html
 

dark-demon

d(^-^)b
Валидация значений при добавлении элементов в коллекцию.
а итераторы тут причём? :)

Массив же могут подменить или испортить, в том числе случайно.
то же самое и с объектом-коллекцией

Более простая реализация отложенных вычислений.
в коллекцию добавляются уже готовые объекты. какие ещё отложенные вычисления?
 

Wicked

Новичок
dark-demon
Валидация значений при добавлении элементов в коллекцию.
а итераторы тут причём? :)
итераторы и коллекции редко рассматриваются раздельно.
то же самое и с объектом-коллекцией
ну-ка поподробнее. На таком примере:
PHP:
final class myCollection ... {
  public function add(myObject $object) {...}
}
function doSmthWithACollection (myCollection $collection) {
  foreach($collection as $object) {...}
}
хочешь сказать, у меня не будет гарантии, что при foreach($collection as $object) {...} у меня в $object появится что-то кроме myObject'ов?
в коллекцию добавляются уже готовые объекты. какие ещё отложенные вычисления?
А причем тут коллекции? :) (с) почти что ты

Как думаешь, SPL'евский RecursiveDirectoryIterator при создании объекта сразу все директории сканирует? .-)
 
Сверху