Как построить дерево из массива

bershadskij

Новичок
Как построить дерево из массива

Помогите написать скрипт, который рекурсивно будет строить дерево из массива
В массиве поле id - ето уникальный идентфикатор, а поле sd - идентификатор, который указывает на родителя.

Что то типа етого:
PHP:
	function tree($nested, $level=0) {
  		$result = array();
  		$item = array_shift($nested);
  			foreach($item as $v=>$k){
                  $item['tree'] = tree($nested, $k['sd']);
   	    		$result[] = $item;
          		$item = array_shift($nested);
              }      	array_unshift($nested, $item);
      	return $result;
  	}
где $nested - ето исходный массиы, $level = родитель
Я никак не разберусь с логикой

сам массив имеет вид
PHP:
Array  (
      [0] => Array
          (
              [id] => 1
              [sd] => 0
              [title] => Ветка 1
          )

        [1] => Array
          (
              [id] => 2
              [sd] => 1
              [title] => Ветка 1.1
          )

        [2] => Array
          (
              [id] => 3
              [sd] => 2
              [title] => Ветка 1.1.1
          )

        [3] => Array
          (
              [id] => 4
              [sd] => 1 
             [title] => Ветка 1.2
          ) 

       [4] => Array
          (
              [id] => 5
              [sd] => 3
              [title] => Ветка 1.2.1
          )

        [5] => Array
          (
              [id] => 6
              [sd] => 4
              [title] => Ветка 1.2.1.1
          )
  )
 

Angerslave

Новичок
Тебе нужно сначала проверять, является ли элемент массива массивом, если да, то снова запускать эту же функцию, иначе - делать вывод в браузер или в переменную.
 

Popoff

popoff.donetsk.ua
bershadskij
а что, в факе совсем-совсем нет подходящего примера? %)
 

avm

Новичок
PHP:
<?php
$array = array (
  array('id' => 1,'parent' => 0,'title' => 'Ветка 1'),
  array('id' => 2,'parent' => 1,'title' => 'Ветка 1.1'),
  array('id' => 3,'parent' => 2,'title' => 'Ветка 1.1.1'),
  array('id' => 4,'parent' => 1,'title' => 'Ветка 1.2'),
  array('id' => 5,'parent' => 3,'title' => 'Ветка 1.2.1'),
  array('id' => 6,'parent' => 4,'title' => 'Ветка 1.2.1.1'),
);

$tree = array();
$sub = array( 0 => &$tree );

foreach ($array as $item)
{
    $id = $item['id'];
    $parent = $item['parent'];

    $branch = &$sub[$parent];
    $branch[$id] = array();
    $sub[$id] = &$branch[$id];
}

print_r($tree);
 
?>
-~{}~ 01.02.07 00:31:

кстати подчиненность заданная в 'sd' не соответствует коментариям "Ветка ..."
 

Popoff

popoff.donetsk.ua
bershadskij
в самом верху этой странички ссылочка называется "вопрос-ответ". там дальше ишешь ссылочку "Способы хранения деревьев в базах данных". ну а потом по смыслу. рекомендую всё поизучать - много интересного там найдёшь.
 

bershadskij

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

я б хотел его немного усовершенствовать.
Я привел его вот к такому виду:

PHP:
	$tree = array();
	$sub = array( 0 => &$tree );
	foreach ($array as $item)
	{
    	$branch = &$sub[$item['sd']];
	   	$branch[$item['id']] = $item;
		$branch[$item['id']]['url'] = "pred_url"."/".$item['url']."/";
		$branch[$item['id']]['href'] = "pred_url"."/".$item['url'].".html";
 		$sub[$item['id']] = &$branch[$item['id']]['tree'];
	}
А как можно добавлять (собирать) урл, при построении дерева?
Вот что то типа етого
PHP:
$branch[$item['id']]['url'] = "pred_url"."/".$item['url']."/";
то-есть вместо "pred_url" подставлять значения всех ['url'] до текущей позиции

исходный массив

PHP:
array(
    [1] => Array
        (
            [id] => 1
            [parent] => 0
            [url] => news
        )

    [2] => Array
        (
            [id] => 2
            [parent] => 1
            [url] => category
        )
)
получить результат

PHP:
array(
    [1] => Array
        (
            [id] => 1
            [parent] => 0
            [url] => news/
			[tree] => Array
			(
			    [2] => Array
 			    (
					[id] => 2
					[parent] => 1
					[url] => news/category/
					[tree] =>
		        )
			)
        )

)
что б получилося => news/category/ и т.д. для всех вложенных категорий
 

Solid

Drosera anglica
Насколько я понимаю, здесь подтекстом идёт "ну напишите за меня ещё немного кода... ну напишите!!! ну... м где же код?".
 

avm

Новичок
bershadskij, а есть ли необходимость? у вас есть исходный линейный массив (правда в нем я например ключами держал значения id) и есть карта подчиненности (то что делает мой код).
Разбор дерева в любом случае будет рекурсивным - вот там и соберёте свой url.

Хотя за символические $50 сделаю так как вы хотите :)

Solid, ага ;)
 

bershadskij

Новичок
>Хотя за символические $50 сделаю так как вы хотите
аааа, вот оно что.
Не, у меня таких денег нет. мож для кого то и символические, но не для меня.
Что ж, буду ждать, может кто забесплатно подскажет.
Но все равно спасибо, avm :)
 

avm

Новичок
bershadskij, прочитайте еще раз то что я написал перед "символическими"... и подумайте - это не плохой выход (ведь линейный массив у вас уже есть, зачем создавать такой же?)
 

bershadskij

Новичок
нет, я не создавать хочу, а заменять елемент массива
=> category на етот же +предыдущий [url] => news/category/ [size=1][i]-~{}~ 01.02.07 23:19:[/i][/size] А вообще, разве плохая реализация? Может кто посоветует получшие, и готовые решения для маленького блога У етого есть свои плюсы: - 1 таблица в базе для хранения дерева - 1 запрос в базу для построения дерева всего сайта
 
Сверху