मैं यहां जो समाधान प्रस्तावित कर रहा हूं वह भौतिक पथ की अवधारणा का उपयोग करता है। आपके नमूना डेटा का उपयोग करते हुए भौतिक पथों का एक उदाहरण निम्नलिखित है। मुझे आशा है कि यह आपको भौतिक पथ अवधारणा को समझने में मदद करेगा:
+----+--------------------------+----------+------------------+
| ID | Name | ParentID | MaterializedPath |
+----+--------------------------+----------+------------------+
| 1 | Parent 1 | 0 | 1 |
| 2 | Parent 2 | 0 | 2 |
| 4 | Parent 2 Child 1 | 2 | 2.4 |
| 6 | Parent 2 Child 1 Child 1 | 4 | 2.4.6 |
| 7 | Parent 2 Child 1 Child 2 | 4 | 2.4.7 |
| 3 | Parent 1 Child 1 | 1 | 1.3 |
| 5 | Parent 1 Child 1 Child | 3 | 1.3.5 |
+----+--------------------------+----------+------------------+
प्रत्येक नोड N
एक भौतिक पथ है, यह पथ आपको रूट नोड से नोड तक जाने का रास्ता बताता है N
. इसे नोड आईडी को जोड़कर बनाया जा सकता है। उदाहरण के लिए, नोड तक पहुँचने के लिए 5
इसके रूट नोड से शुरू करते हुए, आप नोड पर जाएँ 1
, नोड 3
, और नोड 5
, इसलिए नोड 5
भौतिक पथ है 1.3.5
संयोग से, आप जिस क्रम की तलाश कर रहे हैं, उसे भौतिक पथ द्वारा क्रम से प्राप्त किया जा सकता है।
पिछले उदाहरण में, भौतिक पथ एक दूसरे से जुड़े हुए तार हैं, लेकिन मैं कई कारणों से द्विआधारी संयोजन पसंद करता हूं।
भौतिक पथ बनाने के लिए आपको निम्नलिखित पुनरावर्ती CTE की आवश्यकता है:
CREATE TABLE Tree
(
ID int NOT NULL CONSTRAINT PK_Tree PRIMARY KEY,
Name nvarchar(250) NOT NULL,
ParentID int NOT NULL,
)
INSERT INTO Tree(ID, Name, ParentID) VALUES
(1, 'Parent 1', 0),
(2, 'Parent 2', 0),
(3, 'Parent 1 Child 1', 1),
(4, 'Parent 2 Child 1', 2),
(5, 'Parent 1 Child 1 Child', 3),
(6, 'Parent 2 Child 1 Child 1', 4),
(7, 'Parent 2 Child 1 Child 2', 4)
GO
WITH T AS
(
SELECT
N.ID, N.Name, N.ParentID, CAST(N.ID AS varbinary(512)) AS MaterializedPath
FROM
Tree N
WHERE
N.ParentID = 0
UNION ALL
SELECT
N.ID, N.Name, N.ParentID, CAST( T.MaterializedPath + CAST(N.ID AS binary(4)) AS varbinary(512) ) AS MaterializedPath
FROM
Tree N INNER JOIN T
ON N.ParentID = T.ID
)
SELECT *
FROM T
ORDER BY T.MaterializedPath
परिणाम:
+----+--------------------------+----------+----------------------------+
| ID | Name | ParentID | MaterializedPath |
+----+--------------------------+----------+----------------------------+
| 1 | Parent 1 | 0 | 0x00000001 |
| 3 | Parent 1 Child 1 | 1 | 0x0000000100000003 |
| 5 | Parent 1 Child 1 Child | 3 | 0x000000010000000300000005 |
| 2 | Parent 2 | 0 | 0x00000002 |
| 4 | Parent 2 Child 1 | 2 | 0x0000000200000004 |
| 6 | Parent 2 Child 1 Child 1 | 4 | 0x000000020000000400000006 |
| 7 | Parent 2 Child 1 Child 2 | 4 | 0x000000020000000400000007 |
+----+--------------------------+----------+----------------------------+
उपरोक्त रिकर्सिव सीटीई रूट नोड्स से शुरू होता है। रूट नोड के लिए भौतिक पथ की गणना करना बहुत आसान है, यह नोड की आईडी है। अगले पुनरावृत्ति पर सीटीई अपने बच्चे के नोड्स के साथ रूट नोड्स में शामिल हो जाता है। चाइल्ड नोड के लिए भौतिक पथ CN
अपने मूल नोड PN
. के भौतिक पथ का संयोजन है और नोड की आईडी CN
. बाद की पुनरावृत्तियां पेड़ पर एक स्तर नीचे तब तक आगे बढ़ती हैं जब तक कि लीफ नोड्स तक नहीं पहुंच जाती।