Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > PHP: Общие вопросы > Дерево каталогов. Функция добавления нового root`а


Автор: Zhulik 5.6.2007, 20:23
Уважаемые разработчики !
Есть такая ситуация: с помощью РНР вывожу ддерево каталогов из Мускула.
Главные и родительские элементы связаны с помощью таких полей
id --- id_parent  --- priority
1  --- 0         ...
2  --- 1        ...
3  --- 2           .....
Тоисть будет в результате так:
 0 
 |_1
     |_2
и т.д.
Если главные каталоги выводить в порядке возростания приоритета, то как организовать функцию, которая добавляла бы новый каталог между существующими ?
Тогда надо "сдвигать" приоритеты для каждого из рутов ? smile 

Автор: rMaveric 5.6.2007, 20:37
Думаю указывать приоритет вывода будет слишком накладно, если требуется жестко хранить положение элементов, то лучше делай линк на последующий элемент в списке. ТОгда в случае добавления (удаления) элемента тебе достаточно будет изменить всего 1 элемент, а не все элементы в подпапке.

Автор: rMaveric 5.6.2007, 23:12
Также подумай давать ссылку не только на последующий элемент, но и на предыдущий. Больше займет места в базе, но двигаться по элементам будет проще, например для удаления элемента.

Автор: WIPS 6.6.2007, 01:56
Zhulik, можно для задания приоритета использовать префиксное кодирование, тогда для вставки элемента между любыми двумя не придется сдвигать приоритеты других узлов. С префиксными кодами извращаться можно по разному, но для хранения в мускле наверное лучше всего использовать FLOAT (можно будет легко сортировать по приоритету при выборке).

Берем текущие приоритеты и записываем в виде:
0,00
0,01
...
0,99 - величина и разрядность последнего приоритета зависит от к-ва вершин-рутов, хотя можно вставить первые две (приоритеты 0,0 и 0,1), а последующие добавлять по нижеописанному алгоритму.

Алг. поясню на примере. Нам надо добавить вершину между 0,07 и 0,09. 
 1. Если делать втупую. Приоритет новой вершины будет просто плюс единица в следующий младший (след. младший для обоих чисел) разряд от первого числа (т.е. - 0,07 + 0,001 = 0,071). Но это подойдет если у нас добавляется не много вершин, т.к. следующая добавленая вершина (между 0,071 и 0,09) будет иметь приоритет 0,0711, потом 0,07111 и т.д., а точность FLOAT-а хоть и большая, но не бесконечная.
 2. Можно анализировать оба числа не только на разрядность. Т.е. сначала мы вставляем 0,08 (т.е. если есть возможность прибавляем единицу не в след. младший разряд, а просто в младший), потом 0,081, 0,082 ... 0,089, 0,0891, 0,0892 и т.д.

Придется конечно при вставке анализировать приоритеты "соседей", но зато можно не переколбашивать приоритеты всей таблицы  smile 

P.S. Вопрос по моему совсем не по PHP, Zhulik, смотри перенесут твою тему куда нибудь в Алгоритмы и т.п.  smile 

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)