Как стать автором
Обновить

Комментарии 23

Код возможно не будет изначально работать, во время написания статьи я его несколько раз менял для удобства
«возможность перебора через foreach/for»
точнее через foreeach, for — не для этого

«возможность перебора есть у всех обьектов»
всмысле?

Что у вас sql в тегах делает?
SPL :)
Yarrr… извиняюсь
никто не заставляет использовать этот обьект как ассоциативный массив, можно и как обычный, все в Ваших руках
> возможность перебора есть у всех обьектов
с помошью foreach можно перебирать public свойства всех обьектов
Про разгон до скорости компилируемых языков, пожалуйста, поподробней :-)
оптимизаторов куча, кэширующих средств тоже немеряно, как только код и данные попадают в память то о скорости уже не стоит задумываться… одно но — память =)
club.shelek.ru/viewart.php?id=300
я конечно утрировал насчет скорости компилируемых, но разогнать можно очень сильно, до 10 раз :)
Не поддерживается несколько обходов одновременно:

$array = new MyArray(array(7, 8, 9));
foreach($array as $firstKey => $firstValue)
{
  foreach($array as $secondKey => $secondValue)
  {
    print "$firstValue, $secondValue\n";
  }
}

Выводит:
7, 7
7, 8
7, 9


Не работает присваивание вложенным массивам:

$array = new MyArray(array(4, 5, 6, array(7, 8, 9)));
echo $array[3][0], "\n";
$array[3][0] = 100;
echo $array[3][0], "\n";

Выводит 7 и 7.
я не ставил цель сделать замену массива обьектом, я лишь показал работу двух интерфейсов и базовый функционал который реализуется с помошью них, дальше лишь полет Вашей фантазии
вообще, если Вы ожидали такой результат:
7, 7
7, 8
7, 9
8, 7
8, 8
8, 9
9, 7
9, 8
9, 9

то смею Вас огорчить: обьект — ссылочный тип, в отличии от массива
Я (как любой программист) ожидаю, что ваш MyArray будет работать подобно встроенному массиву (хотя бы потому что он так называется и реализует соответствующие интерфейсы). И смотрю не на мелкие особенности, а на самые базовые варианты использования.

Тем более что ваша статья для новичков («продвинутые» уже видели такие фичи и в php, и в других языках). Возьмут, скопируют и будут думать, почему не работает.
на сколько мне известно, любая книга по PHP в самом начале обьясняет что массивы — простой тип данных, обьект — ссылочный, при мизерном стаже работы сразу визуально заметно что массив копируется а обьект ссылается… так что я скорее всего не соглашусь с Вами, не все будут ожидать такого результата

зы: ни разу не приходилось перебирать один массив в двух циклах если честно… на крайняк, если это Вам уж очень надо, можно реализовать клонирование обьекта
Если я второй пример перепишу так, то думаю, что станет понятнее:
doit(new MyArray(array(4, 5, 6, array(7, 8, 9))));
doit(array(4, 5, 6, array(7, 8, 9)));

function doit($data)
{
  echo $data[3][0], "\n";
  $data[3][0] = 100;
  echo $data[3][0], "\n";
}


Мы получили класс, экземпляры которого ведут себя как массивы. Код (функция doit) может даже не знать, с чем он работает, с массивом или с MyArray. Массив нормально реагирует на изменения, а MyArray — нет, причём «тихо», не вызывая ошибок. И присвоенные данные пропадают вникуда.

Два вложенных обхода по одному и тому же массиву вы, непосредственно может и не писали. Но вполне вероятна такая ситуация, что внутри foreach вы вызываете некоторую функцию над этим же массивом, и эта функция тоже обходит массив. Если это будет настоящий массив — всё хорошо. Если MyArray — будете долго отлаживать.
как я писал выше, я не ставил задачу сделать аналог массива, вот Вы прям прицепились к тому что обьект должен работать обязательно как массив и все, это физически не возможно условиями интерпритатора и среды выполнения, так пожелали разработчики
см upd. я надеюсь это обьясняет теперь Ваши удивления?
Просто надо в статье сделать дисклаймер, что пример не является полной эмуляцией массива, хорошо бы с объяснение причин от «сделан только для демонстрации» до " это сделать невозможно" ;)
еще раз повторю: цель топика не обьект для замены массива а обзор 2-х интерфейсов дающих обьекту дополнительные свойства которые нельзя обеспечить стандартными средствами OOP
см upd.
изменил метод offsetGet() теперь работает присваивание влоденным массивам
Давно мучает вопрос:
Вот есть фильтр на SPL для вывода файлов определенного типа из директории
<?php 
class F_FileIterator extends FilterIterator { 
    private $ext; 
    private $it; 

    function __construct(DirectoryIterator $it, $ext) { 
        parent::__construct($it); 
        $this->it=$it; 
        $this->ext=$ext; 
    } 

    function accept() { 
        $ext=pathinfo($this->current(),PATHINFO_EXTENSION); 
        return ($ext==$this->ext) ? true : false; 
    } 


$d=new F_FileIterator(new DirectoryIterator('.'), 'php'); 

foreach ($d as $v) { 
    echo "$v<br />\n"; 

?>



а как сделать компаратор на ооп? Тоесть чтобы они выводились в нужном мне порядке, а не от балды.
вообще, они следуют не от балды а попорядку в файловой системе, как в FilterIterator сделать чтоб он их сортировал, если честно, не знаю, но напрашивается обвертка для всего этого (допустим F_Files) с методом getSorted( )
Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации

Истории