PHP-объектный эквивалент среза массива();

Я пытаюсь удалить первые два элемента в объекте. Например, если бы я хотел удалить первые два элемента из массива, я бы использовал array_slice($arrayName, 2).

Я пробовал это на своем объекте (Эй, почему бы и нет? Я знаю, что это не технически массив, но я оптимист), и это не сработало.

при поиске этого все, что я нашел, были методы удаления элементов из массивов.

    $categories = array_slice(Mage::getModel('catalog/category')->getCollection()->addAttributeToSelect('*'), 2);


    foreach($categories as $category){
        echo "<div class='col'>{$category->getName()}</div>";
    }

В приведенном выше примере, я хочу удалить первые два категории из $categories (которые являются "корневой категорией" и "по умолчанию") объект перед запуском его через цикл foreach. Каков был бы наилучший способ сделать это? Я знаю, что мог бы это сделать;

if($category->getName() != 'Root Category' && $category->getName() != 'Default'){
  echo $category->getName();
}

но это похоже на грязное решение.

редактировать

прочитав комментарий Патрика Q, я понял, что это действительно массив объектов. Итак, мой вопрос теперь становится, почему при применении array_slice к этому массиву это приводит к пустому экрану? Этот цикл отлично работает, когда array_slice не применяется.

Изменить 2

игнорировать последнее редактирование. Это объект.

что касается возможного дублирования, в то время как вопрос (в вопросе) действительно помог мне решить мою проблему, я думаю, по сути это разные вопросы. Этот вопрос, по сути, сосредоточен на поиске полезной альтернативы array_slice () для объектов. Вопрос, связанный с другой стороны, хочет найти способ, в частности, фильтровать Magento коллекции на основе раскрывающегося атрибута. Хотя они, возможно, прибыли в одно и то же место назначения, цель и путешествие очень различны.

2 ответов


функциональность, насколько мне известно, не существует в Magento.

я пытаюсь удалить первые два элемента объект (выделено мной)

по умолчанию объекты PHP не действовать как массивы. В PHP нет внутренней концепции того, что означало бы для объекта иметь первый, второй или третий элемент.

причина, по которой вы можете foreach или count объект коллекции Magento, как будто это был массив, потому что объект базовой коллекции реализует специальные интерфейсы из стандартной библиотеки PHP -- IteratorAggregate и исчисляемыми

#File: lib/Varien/Data/Collection.php
class Varien_Data_Collection implements IteratorAggregate, Countable
{
}

реализуя эти интерфейсом, (по определение методов Varien_Data_Collection по ссылкам руководства выше) объект получает foreach и count() функциональность.

Magento в IteratorAggregate реализация (то, что дает вам foreach функциональность) зависит от встроенного PHP ArrayIterator класс

#File: lib/Varien/Data/Collection.php
class Varien_Data_Collection implements IteratorAggregate, Countable
{
    public function getIterator()
    {
        $this->load();
        return new ArrayIterator($this->_items);
    }
}

и объекты, созданные из ArrayIterator класс нет встроенных функций слайса. Это имеет смысл-концептуально идея за итератор это то, что он позволяет вам пересекать список без загрузки всего базового списка в память сразу. То, что базовые итераторы Magento и PHP работают с уже загруженными массивами,-это немного общей избыточности в OO PHP.

так, если вы хотели использовать slice с объектом коллекции Magento, я бы попробовал getArrayCopy метод базового итератора.

$array = array_slice($categories->getIterator()->getArrayCopy(), 2);

это должно (непроверено) возвращать массив PHP с ожидаемыми нарезанными элементами.

надеюсь, что это поможет!


LimitIterator-это итератор, связанный с версией функции среза. Вы можете использовать его как:

$categories = new LimitIterator(
    Mage::getModel('catalog/category')
    ->getCollection()
    ->addAttributeToSelect('*')
    ->getIterator(), 
    2
);


foreach($categories as $category){
    echo "<div class='col'>{$category->getName()}</div>";
}