Php массив дерева категорий

shurinskiy / category_tree.php

This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode characters

/**
* Пример кода который будет упорядочивать рекурсивно массив и превращать его в дерево по
* идентификаторам родительских элементов — при этом он работает с произвольным уровнем вложенности.
* В этом примере, предпологается использование одной корневой категории, не имеющей потомков.
**/
$v_arr = array(
array(ID = > «0», name = > «корневая», parent= > «-1»),
array(ID = > «1», name = > «первая», parent= > «0»),
array(ID = > «2», name = > «вторая», parent= > «0»),
array(ID = > «3», name = > «третья», parent= > «1»),
array(ID = > «4», name = > «четвертая», parent= > «1»),
array(ID = > «5», name = > «пятая», parent= > «2»),
array(ID = > «6», name = > «шестая», parent= > «2»),
array(ID = > «7», name = > «седьмая», parent= > «5»),
array(ID = > «8», name = > «восьмая», parent= > «5»)
);
$v_tree = array();
/**
* Построить дерево
**/
function make_tree($arr, &$tree, $par_id=-1)
foreach($arr as $item)
if($item[‘parent’] == $par_id)
if( ! is_array($tree))
$tree = array();
>
$tree[$item[‘ID’]] = array(
‘name’ = > $item[‘name’],
‘ID’ = > $item[‘ID’],
‘parentID’ = > $item[‘parent’]
);
make_tree($arr, $tree[$item[‘ID’]], $item[‘ID’]);
>
>
>
/**
* Обойти дерево и преобразовать в список
**/
function menu_output($arr)
$html = »;
foreach($arr as $value)
if(! is_array($value)) continue;
$html .= ‘ < li >‘;
$html .= $value[‘name’];
$html .= menu_output($value);
$html .= ‘ ‘;
>
return $html ? ‘ < ul >‘.$html.’ ‘ : »;
>
make_tree($v_arr, $v_tree); // построить дерево из массива
echo menu_output(array_shift($v_tree)); // избавляюсь от корневого элемента дерева, а остальное вывожу как список

Источник

БЛОГ ПРО WEB

Рассказываю о web-разработке
и помогаю создавать сайты

PHP Категории (Дерево категорий)

Иерархическая

Сегодня наша цель, создать иерархическую структуру категорий. Нам важно чтобы было удобно хранить категории и чтобы было легко выводить их там где нам надо.

Иногда простое кажется сложным, именно по этому выложу несколько фрагментов кода, которые я надеюсь вам пригодятся для реализации php категорий в виде дерева.

Итак, структура должна состоять из id категории (id), из названия категории (name) и конечно id родительской категории (parent_id). В MySQL это выглядит так:

CREATE TABLE IF NOT EXISTS `category` ( `id` int(10) unsigned NOT NULL AUTO_INCREMENT, `name` varchar(255) NOT NULL, `parent_id` int(11) NOT NULL, PRIMARY KEY (`id`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=0 ;

Минимальная и понятная структура таблицы для хранения категорий.

Заполняем таблицу нашими категориями

INSERT INTO `category` (`id`, `name`, `parent_id`) VALUES (1, 'Телефоны и планшеты', '0'), (2, 'Автомобили', '0'), (3, 'Samsung', '1'), (4, 'Apple', '1'), (5, 'LG', '1'), (6, 'Ford', '2'), (7, 'Lexus', '2'), (8, 'BMW', '2'), (9, 'Galaxy Tab 4', '3'), (10, 'Galaxy S6', '3');

Там где значение parent_id=0, у данной категории нет родительской категории.

Тут все понятно и просто. Теперь присутпим к выводу списка категорий. Но для правильного вывода списка, нам нужно сначала получить весь список php категорий, а уже потом с помощью рекурсии сформировать наше дерево. Следующая функция предназначена для получения этого списка:

function get_cat() < //запрос к базе данных $sql = "SELECT * FROM category"; $result = mysql_query($sql); if(!$result) < return NULL; >$arr_cat = array(); if(mysql_num_rows($result) != 0) < //В цикле формируем массив for($i = 0; $i < mysql_num_rows($result);$i++) < $row = mysql_fetch_array($result,MYSQL_ASSOC); //Формируем массив, где ключами являются адишники на родительские категории if(empty($arr_cat[$row['parent_id']])) < $arr_cat[$row['parent_id']] = array(); >$arr_cat[$row['parent_id']][] = $row; > //возвращаем массив return $arr_cat; > >

Дальше нам надо запустить эту функция для получения массива

//получаем массив каталога $result = get_cat();

Теперь нужна функция с рекурсией

Теперь осталось только вывести каталог на экран с помощью рекурсивной функции

И в общем то и всё. Таким образом мы можем получить полное дерево категорий с бесконечными подкатегориями.

Источник

PHP:Как вывести дерево категорий?

введите сюда описание изображения

наткнулся на статью хорошо описано про создания дерево категории, но функция вернет ответь в готовый html но я хочу получать дерево в массиве структура такая:

введите сюда описание изображения

результат в виде html: Вопрос: возможно ли получит дерево категории в виде массива не зависимо от вложенности

ну как бы завернуть дерево в массив а не в готовом html, а почему вы считаете что статья не очень возможно вы знаете более легкий красивый код и логики?

Можно просто ввести левое и правое плечо в базу данных, и level уровень. Выбираете эти данные из базы в одномерный массив с учётом левого и правого плеча. И рендерите одномерный массив на html+css.

ну в статье мне нравится то что все данные хранятся в одно, и не нужно никакого моста между таблицей, в рекурсии даже меньше кода как мне кажется.

Это только элюзия, а вообще li формируеться просто введи результирующий массив вместо $tree и там var_dump . p.s. Рекурсию сложно дебажить к примеру, ` return ` в функции вернёт в выполнение предыдущего вызова функции.

2 ответа 2

Вопрос: возможно ли получит дерево категории в виде массива не зависимо от вложенности ?

Отвечаю на этот вопрос во втором примере ! Хотя и первый тоже может понадобится.В моём коде он выводит категории в dropdown lists(. ) .

Примечание : mysql_fetch_assoc($result) вернёт вам вот такой массив:

$arr = [ [ 'id' => 1, 'parent_id' => 0, 'name' => 'Раздел 1' ], [ 'id' => 2, 'parent_id' => 0, 'name' => 'Раздел 2' ], [ 'id' => 3, 'parent_id' => 0, 'name' => 'Раздел 3' ], [ 'id' => 4, 'parent_id' => 1, 'name' => 'Раздел 1.1' ], [ 'id' => 5, 'parent_id' => 1, 'name' => 'Раздел 1.2' ], [ 'id' => 6, 'parent_id' => 4, 'name' => 'Раздел 1.1.1' ], [ 'id' => 7, 'parent_id' => 2, 'name' => 'Раздел 2.1' ], [ 'id' => 8, 'parent_id' => 2, 'name' => 'Раздел 2.2' ], [ 'id' => 9, 'parent_id' => 3, 'name' => 'Раздел 3.1' ] ]; 

Дальнейшие примеры будут приведены исходя из данного массива $arr ,который может иметь безграничную вложенность иерархий (id -> parent_id ).По крайней мере столько сколько позволено стеков в рекурсии.По моему равен 1000.

1.Результат: Одномерный массив указывающий глубину вложенности через черточку — :

function CreateTree($array,$sub=0,$tab='') < //asort($array); $category=array(); if($sub>0) foreach($array as $v) < if($sub == $v['parent_id'])< $category[$v['id']] = $tab.$v['name']; $category += CreateTree($array,$v['id'],$tab); >> return $category; > echo '
'; print_r(CreateTree($arr)); 

2. Результат: Многомерный массив с иерархической вложенностью:

function CreateTree($array,$sub=0) < $a = array(); foreach($array as $v) < if($sub == $v['parent_id']) < $b = CreateTree($array,$v['id']); if(!empty($b)) $a[$v['name']] = $b; else $a[$v['id']] = $v['name']; >> return $a; > echo "
"; print_r(CreateTree($arr)); 

Источник

Многоуровневое меню на PHP + MySQL

Многоуровневое меню на PHP + MySQL

Ни один сайт не обходится без навигации или как еще называют "меню сайта". Так вот меню сайта бывает одноуровневым и многоуровневым в виде дерева. Если с одноуровневым меню особых сложностей в плане реализации не возникает, то при создании многоуровневого меню нужно хорошо подумать.

Самое главное в этой задаче это спроектировать базу данных для нашего многоуровневого меню. Создадим таблицу Categories с тремя полями id , title , parent где:

  • ID – идентификатор
  • Title – Название меню
  • Parent – Родитель категории по умолчанию 0

За ветвление меню отвечает поле Parent если Parent = 0 , то эта категория является родительской. Для того чтобы добавить потомков к родительской категории нужно в поле parent указать ID нужного родителя. Например:

Таблицы с категориями
ID TITLE PARENT
1 Автомобили 0
2 Мотоциклы 0
3 Мазда 1
4 Хонда 1
5 Кавасаки 2
6 Харлей 2
7 Лодки 0

Как видно из таблицы, у родительской категории Автомобили есть два потомка – это Мазда и Хонда связанных по полю Parent . А у категории Мотоциклы два потомка – это Кавасаки и Харлей . При этом у категории Лодки нет потомков. Надеюсь, что Вы поняли,как связать категории.

Далее переходим от слов к практике. Создадим таблицу Categories.

 CREATE TABLE IF NOT EXISTS `categories` ( `id` int(10) unsigned NOT NULL AUTO_INCREMENT, `title` varchar(255) NOT NULL, `parent` int(10) unsigned NOT NULL, PRIMARY KEY (`id`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=20 ; -- -- Дамп данных таблицы `categories` -- INSERT INTO `categories` (`id`, `title`, `parent`) VALUES (1, 'Автомобили', 0), (2, 'Мотоциклы', 0), (3, 'Мазда', 1), (4, 'Хонда', 1), (5, 'Кавасаки', 2), (6, 'Харлей', 2), (7, 'Мазда 3', 3), (8, 'Мазда 6', 3), (9, 'Седан', 7), (10, 'Хечбэк', 7), (11, 'Лодки', 0), (12, 'Лифтбэк', 8), (13, 'Кроссовер', 8), (14, 'Белый', 13), (15, 'Красный', 13), (16, 'Черный', 13), (17, 'Зеленый', 13), (18, 'Мазда CX', 3), (19, 'Мазда MX', 3); 

Алгоритм работы состоит из следующего:

  • Создаем соединение с базой данных
  • Получаем все данные из таблицы Categories
  • Обрабатываем полученные данные изменив ключ массива на номер ID
  • Из обработанного массива строим дерево зависимостей неограниченной вложенности используя метод рекурсии для построения
  • Выводим наше многоуровневое меню на экран

Создаем соединение с базой данных

 query("SET NAMES 'utf8'"); /* * Это "официальный" объектно-ориентированный способ сделать это * однако $connect_error не работал вплоть до версий PHP 5.2.9 и 5.3.0. */ if ($mysqli->connect_error) < die('Ошибка подключения (' . $mysqli->connect_errno . ') ' . $mysqli->connect_error); > /* * Если нужно быть уверенным в совместимости с версиями до 5.2.9, * лучше использовать такой код */ if (mysqli_connect_error())

Пишем функцию получения данных из таблицы Categories

 //Получаем массив нашего меню из БД в виде массива function getCat($mysqli)< $sql = 'SELECT * FROM `categories`'; $res = $mysqli->query($sql); //Создаем масив где ключ массива является ID меню $cat = array(); while($row = $res->fetch_assoc()) < $cat[$row['id']] = $row; >return $cat; > 

Получаем массив вот такого вида, где ключ массива это ID категории.

Многоуровневое меню на PHP + MySQL

Далее нам нужно из этого массива построить дерево зависимости дочерних элементов от родительских проходя рекурсивно по всему массиву.

Функция построения дерева из массива от Tommy Lacroix

 //Функция построения дерева из массива от Tommy Lacroix function getTree($dataset) < $tree = array(); foreach ($dataset as $id =>&$node) < //Если нет вложений if (!$node['parent'])< $tree[$id] = &$node; >else < //Если есть потомки то перебераем массив $dataset[$node['parent']]['childs'][$id] = &$node; >> return $tree; > 

Получаем массив в виде дерева

Многоуровневое меню на PHP + MySQL

Скрипт целиком

Результат работы

Многоуровневое меню на PHP + MySQL для админки

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

 '.$category['title'].''; >else< $menu = ''; > if(isset($category['childs'])) < $i = 1; for($j = 0; $j < $i; $j++)< $str .= '→'; >$i++; $menu .= showCat($category['childs'], $str); > return $menu; > /** * Рекурсивно считываем наш шаблон **/ function showCat($data, $str) < $string = ''; $str = $str; foreach($data as $item)< $string .= tplMenu($item, $str); >return $string; > //Получаем HTML разметку $cat_menu = showCat($tree, ''); //Выводим на экран echo ''; ?> 

Источник

Читайте также:  Размер приствольного круга плодовых деревьев
Оцените статью