Всем добрый вечер! Кризис коснулся всех, меняю работу, прохожу собеседование. 3 задания выполнил без труда. Последнее задание показываю на суд общественности: --------------- Реализовать класс Collection, который бы хранил в виде ассоциативного массива набор данных. Предполагается, что у данного класса есть всего два метода set(name, value) и get(name). Также, помимо этого, нужно реализовать класс CollectionIterator и интерфейс Iterator в соответствии с паттерном Iterator. После создания вышеперечисленного нужно сделать какой-нибудь пример, показывающий работу данных классов. --------------- С паттерном итератор в индексированном массиве все абсолютно понятно, но в ассоциативном массиве, я даже представить не могу его реализацию. Ведь в нем данные не упорядочены и доступ к ним осуществляются по ключам. В данном задание как мне кажется, создается объект типа Collection, вносим туда несколько значений с определенными ключами. Каким образом класс CollectionIterator может узнать о том, под какими ключами хранятся объекты, не говоря уже об их последовательности. Что кто по этому поводу думает, может кто то знает как это возможно сделать?
флоппик я думаю это не совсем то, мне нужно написать свою реализацию итератора для аасоциативного массива. А в примере по ссылке используется функциия getIterator().
http://www.php.net/~helly/php/ext/spl/ ну так там видно, как он работает. Почитай. Тебе нужно, что бы он интерфейс Seekable реализовал. Это обычно реализуется заведением внутренним указателем на текущую позицию в коллекции, и методы для его перемещения.
Маленькое дополнение: Дело в том, что в данном задание как я понял, массив хранится в классе Collection, с полем доступа private. У этого класса два метода set(name, value) и get(name), по условию. Т.е. из класса CollectionIterator я не могу обратится к массиву, я могу лишь получить значение по определенному ключу, о которых класс CollectionIterator не имеет ни какого представления.
Как мне кажется никаие стандартные интерфейсы мне не помогут, доступ к массиву я не имею, могу лишь только обратится по двум методам, get и set. Вообщем походу задание я провалю или его реализация с данными условиями невозможна. Вот код класса Collection: PHP: class Collection { private $list; function __construct() { $this->list = array(); } function set($name,$value){ $this->list[$name]=$value; } function get($name) { return $this->list[$name]; } }
cherkashin-vova, Ну так подумай о том, что бы итератор унаследовать от массива - ты и получишь доступ к его данным.
cherkashin-vova Насколько я понял, CollectionIterator должен наследовать Collection и методы next, prev, seek, current. Через соответствующие функции next, prev, reset и current. А доступ к самому массиву в любом случае нужен, и наследование здесь самый правильный подход. Еще вариант взять готовый ArrayObject и ArrayIterator Это называется абстракция. И то, что сейчас, в текущей реализации, данные хранятся в массиве вовсе не значит, что потом они будут хранится также. И если об этом не подумать заранее, то потом придется бегать по коду, включая все модули, ломать устоявшийся API (почему не устанавливается модуль, почему не работает, а у меня выдает ошибку, вот ведь идиоты эти разработчики…) и еще куча проблем.
PHP: <?php interface Collection extends Iterator { public function add( $o ); public function get( $index ); public function set( $index, $o ); public function remove( $index ); public function size( ); } class ArrayList implements Collection { private $data = array(); public function __construct(array $array=array()) { $this->data = array_values($array); } /** Methods that implements from Iterator */ public function current() { return current($this->data); } public function key() { return key($this->data); } public function next() { next($this->data); } public function rewind() { reset($this->data); } public function valid() { return (current($this->data) !== false); } /* /Methods from Iretatar */ /** Methods from Collection */ public function add($o) { $this->data[] = $o; } public function get( $index ) { return isset($this->data[$index])?$this->data[$index]:null; } public function size() { return count($this->data); } public function toArray() { return $this->data; } public function remove( $index ) { if (isset($this->data[$index])) { unset($this->data[$index]); } } public function set( $index, $o ) { $this->data[(int)$index] = $o; } } возможно даж работает