Поиск крошек для вложенных наборов

Я использую вложенные наборы (или измененный обход дерева предзаказа) для хранения списка групп, и я пытаюсь найти быстрый способ создания хлебных крошек (в виде строки, а не таблицы) для ВСЕХ групп одновременно. Мои данные также хранятся с использованием модели списка смежности (есть триггеры для синхронизации двух).

Так, например:

ID   Name    ParentId  Left   Right
0    Node A  0         1      12
1    Node B  0         2      5
2    Node C  1         3      4
3    Node D  0         6      11
4    Node E  3         7      8
5    Node F  4         9      9

Который представляет дерево:

Узел АУзел БУзел СУзел ДУзел ЕУзел F

Я хотел бы иметь возможность иметь пользовательскую функцию, которая возвращает таблицу:

ID  Breadcrumb
0   Node A
1   Node A > Node B
2   Node A > Node B > Node C
3   Node A > Node D
4   Node A > Node D > Node E
5   Node A > Node D > Node F

Чтобы сделать это немного сложнее (хотя это и выходит за рамки вопроса), у меня также есть ограничения пользователей, которые необходимо соблюдать. Так, например, если у меня есть доступ только к id = 3, при запуске запроса я должен получить:

ID  Breadcrumb
3   Node D
4   Node D > Node E
5   Node D > Node F

У меня есть пользовательская функция, которая принимает идентификатор пользователя в качестве параметра и возвращает таблицу с идентификаторами всех групп, которые являются действительными, так долго, как где-то в запросе

WHERE group.id IN (SELECT id FROM dbo.getUserGroups(@userid))

это будет работать.

У меня есть существующая скалярная функция, которая может сделать это, но она просто не работает с любым разумным количеством групп (занимает более 10 секунд на 2000 групп). Он принимает groupid и userid в качестве параметра и возвращает nvarchar. Он находит родителей заданных групп (1 запрос для захвата левого / правого значений, другой - для поиска родителей), ограничивает список группами, к которым у пользователя есть доступ (с использованием того же предложения WHERE, что и выше, поэтому еще один запрос), и затем использует курсор, чтобы пройти каждую группу и добавить ее в строку, прежде чем, наконец, вернуть это значение.

Мне нужен метод для этого, который будет работать быстро (например, <= 1 с) на лету.

Это на SQL Server 2005.

Ответы на вопрос(6)

Ваш ответ на вопрос