Модераторы: skyboy
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Получить всех родителей элемента в дереве 
V
    Опции темы
zammar
Дата 18.9.2009, 17:43 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 289
Регистрация: 30.10.2008

Репутация: нет
Всего: нет



user posted image

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

Например, для 4 получить идентификаторы 2-ки и 1-ы
для 2-ки идентификатор 1

id    name    left    right       level 
1     eee       0         11          1
2     sss        1         6            2
3     www     7        10           2
4    ggg        2         3            3
5    jjj           4         5            3
6    ooo        8         9            3

PM   Вверх
Gluttton
Дата 18.9.2009, 17:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Начинающий
***


Профиль
Группа: Завсегдатай
Сообщений: 1170
Регистрация: 28.8.2008
Где: Феодосия

Репутация: 24
Всего: 54



Не совсем понятно (мне), а точнее совсем не понятно smile , на основании каких данных? Что храниться в left и right?
СУБД?


--------------------
Слава Україні!
PM MAIL   Вверх
Zloxa
Дата 18.9.2009, 19:57 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3473
Регистрация: 12.9.2008

Репутация: 53
Всего: 161



Цитата(Gluttton @  18.9.2009,  17:57 Найти цитируемый пост)
Что храниться в left и right?

Судя по всему дерево представлено в виде nested sets


--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
Gluttton
Дата 18.9.2009, 20:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Начинающий
***


Профиль
Группа: Завсегдатай
Сообщений: 1170
Регистрация: 28.8.2008
Где: Феодосия

Репутация: 24
Всего: 54



Цитата(Zloxa @  18.9.2009,  19:57 Найти цитируемый пост)
Судя по всему дерево представлено в виде nested sets

Здорово, открыл для себя nested sets smile ...


--------------------
Слава Україні!
PM MAIL   Вверх
Zloxa
Дата 18.9.2009, 20:24 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3473
Регистрация: 12.9.2008

Репутация: 53
Всего: 161



Цитата(Gluttton @  18.9.2009,  20:09 Найти цитируемый пост)
Здорово, открыл для себя nested sets smile ... 

в FB есть рекурсивные запросы, этот анонизгемморой тебе врядли там понадобится. Получается сейчас наверное только MySQL не умеет рабоать с деревьфми. Однако ключевые слова для поиска, навсяк, запомнить желательно бы, ну и ключевой принцип тоже ;)


--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
Gluttton
Дата 18.9.2009, 22:37 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Начинающий
***


Профиль
Группа: Завсегдатай
Сообщений: 1170
Регистрация: 28.8.2008
Где: Феодосия

Репутация: 24
Всего: 54



Ну теперь, когда я теоретически подкован smile, приведу свои варианты (если в этом ещё остался смысл smile )...
Таблица:
user posted image
Первый вариант я списанал адаптировал smile из приведенного Zloxой источника:
Код

select id
from nt
    where left<=2 AND right>=3 order by left

Результат:
user posted image
Второй вариант, я написал, вдохновлённый реализацией рекурсивных запросов в Firebird:
Код

with recursive
    sub as
    (
        select cast(nt.id as varchar(10)) as id, nt.left, nt.right, nt.level
        from nt
        union all
        select cast(sub.id as varchar(10))||'-'||cast(nt.id as varchar(10)) as id, nt.left, nt.right, nt.level
        from sub, nt
            where sub.level=nt.level+1
            and
            (
                nt.left=sub.left-1
                or
                nt.right=sub.right+1
            )
    )
select
    max(sub.id)
from sub
    where substring(sub.id from 1 for 1)='4'

Результат:
user posted image
*
- запросы выполнялись на Firebird 2.1;
- left, right, level - зарезервированные слова Firebird 2.1, и для использования необходимо помещать их в двойные кавычки (и что меня очень удевило приводить к верхнему регистру  smile ?).

Zloxa,
Цитата(Zloxa @  18.9.2009,  20:24 Найти цитируемый пост)
в FB есть рекурсивные запросы, этот анонизгемморой тебе врядли там понадобится. Получается сейчас наверное только MySQL не умеет рабоать с деревьфми.

Т.е. nested sets необходимы только в том случае если нет рекурсии? А если есть (в смысле реализована) рекурсия, то деревья можно строить используя parent_id?


--------------------
Слава Україні!
PM MAIL   Вверх
Zloxa
Дата 19.9.2009, 02:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3473
Регистрация: 12.9.2008

Репутация: 53
Всего: 161



Цитата(Gluttton @  18.9.2009,  22:37 Найти цитируемый пост)

Т.е. nested sets необходимы только в том случае если нет рекурсии? А если есть (в смысле реализована) рекурсия, то деревья можно строить используя parent_id? 

тип того.
nested sets безумно дорогие на модификацию. Фактически этот способ хранения применим только для весьма статичных данных с очень невеликим объемом./*О конкурентной модификации я, если честно, пока даже не размышлял ибо мысль об обдумывании стратегии конкурентной модификации меня заведомо ввергает в ужос. Хотя, может, там все просто и думать придется лишь самую малость. Но буде мне пришлось бы реализовывать такую модель, я таки бы смалодушничал и впопервой, пока не подумал, проводил бы модификации в режиме монопольного доступа.*/
Однако, стоит заметить, этот метод хранения, таки дает существенные преимущества на выборке.

Это сообщение отредактировал(а) Zloxa - 19.9.2009, 02:50


--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
zammar
Дата 19.9.2009, 08:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 289
Регистрация: 30.10.2008

Репутация: нет
Всего: нет



Извиняюсь, база MySQL.
Я не совсем правильно задал вопрос. Мне нужно достать все элементы и для каждого всех его родителей.
Это можно сделать только запросом в цикле как мне думается или все таки как-то можно это сделать одним запросом?

Ну а метод который предложил Gluttton лежит конечно на поверхности. Но все равно спасибо.

Код

select id
from nt
    where left<=2 AND right>=3 order by left

PM   Вверх
Gluttton
Дата 19.9.2009, 22:29 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Начинающий
***


Профиль
Группа: Завсегдатай
Сообщений: 1170
Регистрация: 28.8.2008
Где: Феодосия

Репутация: 24
Всего: 54



Цитата(zammar @  19.9.2009,  08:57 Найти цитируемый пост)
Мне нужно достать все элементы и для каждого всех его родителей.

Для указанных выше исходных данных, приведенный ниже запрос
Код

select
    nta.id as children,
    ntb.id as parent
from nt as nta, nt as ntb
    where ntb.left<nta.left
    and ntb.right>nta.right
    order by nta.id

Вернет следующие данные:
user posted image
Цитата(zammar @  19.9.2009,  08:57 Найти цитируемый пост)
Это можно сделать только запросом в цикле как мне думается или все таки как-то можно это сделать одним запросом?

Что за императивные взгляды в декларативном мировозрении smile ?
Цитата(zammar @  19.9.2009,  08:57 Найти цитируемый пост)
Ну а метод который предложил Gluttton лежит конечно на поверхности. Но все равно спасибо.

Всё равно пожалуйста...

Подумал тут на досуге...
Правильнее будет так:
Код

select
    nta.id as children,
    ntb.id as parent
from nt as nta
    left join nt as ntb
    on
    (
        ntb.left<nta.left
        and 
        ntb.right>nta.right
    )
    order by nta.id

И тогда результат буде таким:
user posted image

Это сообщение отредактировал(а) Gluttton - 20.9.2009, 10:26


--------------------
Слава Україні!
PM MAIL   Вверх
Zloxa
Дата 19.9.2009, 22:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3473
Регистрация: 12.9.2008

Репутация: 53
Всего: 161



Цитата(zammar @  19.9.2009,  08:57 Найти цитируемый пост)
Мне нужно достать все элементы и для каждого всех его родителей.

приведите ожидаемый Вами результат запроса.


--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
gcc
Дата 21.9.2009, 04:21 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Агент алкомафии
****


Профиль
Группа: Участник
Сообщений: 2691
Регистрация: 25.4.2008
Где: %&й

Репутация: нет
Всего: 17



все дерево в низ:
Код

SELECT id_se
                              FROM section
                            WHERE
                    parent_se_id = 55
                      
                    UNION
                      
                    SELECT t1.id_se
                    FROM
                    section t1 JOIN section t2
             ON t1.parent_se_id = t2.id_se
                    WHERE
              t2.parent_se_id = 55


смотря какое дерево все таки,  в большинстве случаев достаточно просто parent

была статья opennet.ru nestedset на innodb с дополнительной таблицей и внешними ключами, транззакцией в 6 раз быстре обычного nestedset при UPDATE INSERT 

но innodb наверное будет грузить сервер больше чем MyISAM
PM WWW ICQ Skype GTalk Jabber   Вверх
zammar
Дата 21.9.2009, 13:00 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 289
Регистрация: 30.10.2008

Репутация: нет
Всего: нет



Gluttton, спасибо. То что нужно.
Всем спасибо!

PM   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Составление SQL-запросов | Следующая тема »


 




[ Время генерации скрипта: 0.0816 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.