Na wszelki wypadek, te rozwiązania są oparte na porównaniach ciągów znaków, nie są zoptymalizowane i nie mogą używać indeksów. powinieneś rozważyć znormalizowanie tabel w inny sposób. (Zobacz Zarządzanie danymi hierarchicznymi w MySQL )
Odnośnie niektórych pytań:
Zaznacz wszystkie dzieci o identyfikatorze 9:
Od Path
kolumna nie zawiera wiodących i końcowych ukośników, należy je połączyć ze ścieżką:
SELECT *
FROM tester
WHERE CONCAT('/', path, '/') LIKE '%/9/%';
wybierz łączną liczbę dzieci dziewiątki, x poziomy głębokości:
Musimy pogrupować według liczby ukośników w ścieżce minus liczba ukośników w ścieżce nadrzędnej:
SELECT (LENGTH(c.Path) - LENGTH(REPLACE(c.Path, '/', '')))
- (LENGTH(p.Path) - LENGTH(REPLACE(p.Path, '/', ''))) AS Level,
COUNT(*)
FROM tester c
JOIN tester p ON c.Parent = p.ID
WHERE CONCAT('/', path, '/') LIKE '%/9/%';
GROUP BY 1
Dla uproszczenia użyłem powyższego zapytania, aby pokazać wszystkie poziomy. Jeśli chcesz ograniczyć głębokość x poziomów, użyj WHERE
predykat z poniższego zapytania.
wybierz identyfikator dzieci 9 do x poziomów, z poziomem w stosunku do 9:
Przeszukujemy Path
kolumna do x poziomów, biorąc pod uwagę poziom rodziców:
SELECT c.*
FROM tester c
JOIN tester p ON c.Parent = p.ID
WHERE CONCAT(
'/',
SUBSTRING_INDEX(
Path,
'/',
(LENGTH(p.Path) - LENGTH(REPLACE(p.Path, '/', ''))) + 4
),
'/') LIKE '%/9/%'
Kroki, które podejmujemy:
- Musimy dowiedzieć się, jak głęboki jest rodzic, możemy to znaleźć, licząc ukośniki na ścieżce rodzica. (
LENGTH(p.Path) - LENGTH(REPLACE(p.Path, '/', ''))
) - Musimy dodać 1 do tej liczby, ponieważ ścieżka z 1 ukośnikiem ma 2 poziomy głębokości.
- Dodajemy x liczbę żądanych poziomów.
- Chwyć kolumnę ścieżki do poziomu całkowitego (użyj
SUBSTRING_INDEX
funkcja). - Dodaj początkowy i końcowy ukośnik.
- Wyszukaj w ostatnim ciągu znaków 9.