Intereting Posts
PHP – разбиение массива на запрос Как правильно использовать сеансы для динамических страниц Codeigniter Download Helper повреждает .7z и .rar файлы помощи или альтернативных решений? Перемещаемость и возврат Узнайте номера страниц файлов PDF, Docx, Doc, Ppt, Pptx с PHP Как добавить дополнительные поля и связанные геттеры / сеттеры из внешнего файла в один или несколько объектов Symfony / Doctrine, без наследования? Таблица Sql импортирует только первый столбец Можете ли вы получить имя пользователя Windows (AD) в PHP? PHP AES 128 ECB Ciphers и Delphi AES 128 ECB single Вставить запрос для вставки нескольких строк в один столбец php – найти, если массив содержит элемент Opencart: Как включить скрипт на определенные страницы? Laravel 5 и WordPress 4.1.1 на одном сервере Использование createNativeQuery для объединения двух объектов без внешнего ключа Получить значение выбранного параметра из выпадающего списка в том же файле в php?

Как я могу получить все дерево в одном запросе с помощью доктрины?

Этот фрагмент с официального сайта работает так, как ожидалось:

$treeObject = Doctrine::getTable('Category')->getTree(); $rootColumnName = $treeObject->getAttribute('rootColumnName'); foreach ($treeObject->fetchRoots() as $root) { $options = array( 'root_id' => $root->$rootColumnName ); foreach($treeObject->fetchTree($options) as $node) { echo str_repeat(' ', $node['level']) . $node['name'] . "\n"; } } 

Но я вижу, что в базу данных отправляются десятки запросов.

Как я могу сделать это во рту?

Solutions Collecting From Web of "Как я могу получить все дерево в одном запросе с помощью доктрины?"

Попробуй это:

 Doctrine_Core::getTable('YourTableWithTree')->createQuery('tree') ->addOrderBy('tree.root_id ASC') ->addOrderBy('tree.lft ASC'); 

Существует алгоритм, построенный в O (n), который строит полное дерево с m уровнями без учета порядка сбора

https://gist.github.com/mmoreram/6292326

Вы можете получить доступ к базовой таблице, как обычная таблица в Doctrine, с запросом, созданным с помощью getBaseQuery() . API не имеет описания для этого метода, но проверьте исходный код:

 public function getBaseQuery() { if ( ! isset($this->_baseQuery)) { $this->_baseQuery = $this->_createBaseQuery(); } return $this->_baseQuery->copy(); } // ... private function _createBaseQuery() { $this->_baseAlias = "base"; $q = Doctrine_Core::getTable($this->getBaseComponent()) ->createQuery($this->_baseAlias) ->select($this->_baseAlias . '.*'); return $q; } 

Просто просмотрите всю таблицу с помощью DQL-запроса, прежде чем смотреть на дерево. Доктрина достаточно умен, чтобы увидеть, что она уже загрузила узлы дерева.

Например

 $q = Doctrine_Query::create()->from('Category c')->orderBy('c.level'); $categories = $q->execute(); 

Если в вашей таблице есть n деревьев (т. Е. N корневых узлов), то первые n объектов в $ категориях являются вашими корнями деревьев.

В зависимости от вашего варианта использования вы можете захотеть сортировать или гидратировать по-разному. Например, чтобы распечатать дерево (например, в вашем примере), вы можете сделать это:

 $q = Doctrine_Query::create() ->select('c.name, c.level') ->from('Category c'); ->orderBy('c.lft') ->setHydrationMode(Doctrine::HYDRATE_SCALAR); $categories = $q->execute(); foreach ($categories as $category) { print str_repeat(' ', $category['c_level']) . $category['c_name'] . "\n"; } 

Это приводит к одному запросу.

Разве это не трюк?

 $treeObject = Doctrine::getTable('Category')->getTree(); $tree = $treeObject->fetchTree(); foreach ($tree as $node) { echo str_repeat('  ', $node['level']) . $node['name'] . "\n"; }