كيفية الحصول على الوالد إعطاء الطفل في SQL Server 2005
-
12-09-2019 - |
سؤال
لدي طاولة مثل هذا
childid parentid
------------------------
1 0
2 1
3 2
4 2
5 3
6 4
7 0
8 7
9 8
10 1
إذا أعطيت طفلا على النحو 5، فإن Parentid سيكون 1 (إخراج)
إذا أعطيت طفلا باسم 9، فستكون الأبوةيد 7. (الإخراج)
أي الجذر الأبوية هو 0 والاستعلام يجب أن يتوقف هناك.
كيفية حل مثل هذا الاستعلام؟
الرجاء المساعدة.
المحلول
أعتقد أنه يجب عليك إعادة تسمية طفلك إلى العقدة، والملب الخاص بك إلى الطفل. Naming العمود الخاص بك مربكة بعض الشيء
create table stack_overflow
(
node int, child_of int
);
insert into stack_overflow(node, child_of) values
(1,0),
(2,1),
(3,2),
(4,2),
(5,3),
(6,4),
(7,0),
(8,7),
(9,8),
(10,1);
هذا يعمل على أي RDBMS قادرة CTE:
with find_parent(parent, child_of, recentness) as
(
select node, child_of, 0
from stack_overflow
where node = 9
union all
select i.node, i.child_of, fp.recentness + 1
from stack_overflow i
join find_parent fp on i.node = fp.child_of
)
select top 1 parent from find_parent
order by recentness desc
انتاج:
parent
7
عدل: أكثر مرونة وموادا في المستقبل:
with find_parent(node_group, parent, child_of, recentness) as
(
select node, node, child_of, 0
from stack_overflow
where node in (5,9)
union all
select fp.node_group, i.node, i.child_of, fp.recentness + 1
from stack_overflow i
join find_parent fp on i.node = fp.child_of
)
select q.node_group as to_find, parent as found
from find_parent q
join
(
select node_group, max(recentness) as answer
from find_parent
group by node_group
) as ans on q.node_group = ans.node_group and q.recentness = ans.answer
order by to_find
انتاج:
to_find found
5 1
9 7
إذا كنت تستخدم postgres., ، يمكن تقصير الرمز أعلاه إلى:
with recursive find_parent(node_group, parent, child_of, recentness) as
(
select node, node, child_of, 0
from stack_overflow
where node in (5,9)
union all
select fp.node_group, i.node, i.child_of, fp.recentness + 1
from stack_overflow i
join find_parent fp on i.node = fp.child_of
)
select distinct on (node_group) node_group as to_find, parent as found
from find_parent
order by to_find, recentness desc
متميزة على الصخور! :-)
نصائح أخرى
إذا كان كل ما تريده هو أصل الجذر، فيمكنك استخدام هذه الوظيفة العودية:
CREATE FUNCTION test_func
(
@ParentID int
)
RETURNS int
AS
BEGIN
DECLARE @result int;
DECLARE @childID int;
SET @childID = (SELECT ChildID FROM YourTable WHERE ParentID = @ParentID)
IF (@childID = 0)
SET @result = @ParentID
ELSE
SET @result = dbo.test_func(@childID)
RETURN @result
END
GO
ثم في الاستعلام الرئيسي الخاص بك:
SELECT dbo.test_func(5)
تمر في 5 عائدات 1، 9 إرجاع 7 بناء على بياناتك المقدمة. إذا كنت بحاجة إلى كل PELTID الذي يرتفع هذه السلسلة، فيجب عليك استخدام CTE.
أعتقد أنك تريد استعلاما متكررا، يجب عليك استخدام تعبيرات الجدول المشترك. سأقدم لك رابطا بمثال مشابه جدا أن الشخص الذي تستخدمه.
أظن هنا هو الحل. لقد ساعدني منذ بضعة أشهر.
بسيطة من مثال الحصول على معرف الأصل مطابقة معرف الطفل معين هو:
select parentid
from MyTable
where childid = 5
ومع ذلك، بالنسبة للبيانات أعلاه، سيعود هذا أي سجلات.