Общие > Базы данных

Запрос запроса запроса...

(1/2) > >>

Mrh:
Казалась бы простая задача.
База:
ID, Parent_ID, Name

Это таблица с деревом каталогов. Родитель наивысшего уровня имеет Parent_ID = 0 соответственно... Глубина - любая.

Нужно "развернуть" полную структуру каталогов, к примеру:


--- Код: ---
Рыбы
Рыбы -> Тропические
Рыбы -> Глубоководные
Рыбы -> Глубоководные -> C ушами
Рыбы -> Глубоководные -> В полушубке
Рыбы -> Глубоководные -> Без глаз
Звери
Звери -> Дикие
--- Конец кода ---

...

Но возникла грабля, поскольку глубина любая (к примеру PHP):

$ID_Start = 0;
$sectQuery = "SELECT ID,Name FROM section WHERE Parent_ID = \'$ID_Start\'";
$sectResult = MySQL_Query ($sectQuery);
echo "<select name=ID>\\n";
while (list ($ID_Start,$Name) = MySQL_Fetch_Row ($sectResult)):
    echo "<option value=$ID_Start>$Name\\n";
    //Тут бесконечная вставка - "отлистыватель"

... Каков алгоритм, чтобы не нужно было делать бесконечную вставку?

Макс:
Почему вставка бесконечная, она ведь равна количеству разделов в таблице.

--- Цитировать ---Казалась бы простая задача.
--- Конец цитаты ---
Для мускуля дерево - задача не такая уж простая (ИМХО).
Первое что приходит в голову - примерно так:
1.Формируешь SQL-запрос так, что бы сразу у тебя все эаписи были в необходимом порядке. (ID и ParentID для этого недостаточно ИМХО).
2. Собираешь в массив строки, к которым может быть присоединена текущая строка (его постоянно прийдется менять).
К примеру перед обработкой строки N6 твоего примера ("Без глаз") в массиве должны быть три строки (Рыбы | Глубоководные | В полушубке ) а после ее обработки в массиве уже должно быть (Рыбы | Глубоководные | без глаз )

Короче, если ты ничего не понял и если никто ничего более понятного не предложит - пиши, буду разжевывать (а то сам понимаю, а популярно объяснить - проблема) :(.

Боря Елкин:
Если дерево, то это рекурсия. Я уже приводил пример обхода http://forums.webscript.ru/showthread.php?s=&postid=17691#post17691 каталога, сейчас попробуем адаптировать к обходу дерева на mysql.

PHP не знаю, нарисую смесь Perl и ПХП.

sub readdirs #читаем дерево каталога
{

$ID_Start=shift;
$In_Name=shift;
my $ret;
$sectQuery = "SELECT ID,Name FROM section WHERE Parent_ID = \'$ID_Start\'";
$sectResult = MySQL_Query ($sectQuery);
return if !$sectResult;

while (list ($ID_Start,$Name) = MySQL_Fetch_Row ($sectResult)){
    $ret.="$In_Name -> $Name\\n";
    $ret.=readdirs($ID,"$In_Name -> $Name");
}

return $ret;
}

Алгоритм примерно такой.

Макс:

--- Цитировать ---Если дерево, то это рекурсия.
--- Конец цитаты ---
Не обязательно.
Можно и одним select-ом дерево вытаскивать. На phpclub мне посоветовали алгоритм "Nested Sets" (вроде так называется) но я его пока не использовал и не разбирался.
В фидо как-то один парень предложил такой алгоритм:
Ввести в таблицу поле (назову его Number) и это поле будет порядковым номером данного элемента в дереве. И сортируя по number получаем на выходе дерево. А при вставке нового элемента в середину дерева все элементы которые будут ниже его изменяют свой number на +1.

Недостаток - тормоза при добавлении элемента в дерево. У меня получилось 2-4 запроса к БД при добавлении элемента.

Боря Елкин:
ОК, тебе лучше знать, я всего лишь предложил тебе рабочий вариант решения.

Навигация

[0] Главная страница сообщений

[#] Следующая страница

Sitemap 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 
Перейти к полной версии