2009-12-14 26 views
1

所以我在SQL-Server數據庫中有一個樹形結構。每個節點通過一個名爲prev的外鍵鏈接到它的父節點,並鏈接到另一個節點。Linq-to-sql:如何主動抓取鏈接的對象?

我希望每當我獲取一個節點時,也會獲取所有導向樹根的節點。目前我可以這樣做:

 MyDataContext db = new MyDataContext(); 
     IList<Node> nodes = new List<Node>(); 
     Node node = db.Nodes.Single(x => x.id == 14); 
     nodes.Add(node); 
     while (node.prev != null) 
     { 
      node = db.Nodes.Single(x => x.id == node.prev); 
      nodes.Add(node); 
     } 

但是這將需要大量的查詢等於我的樹的深度。我對linq-to-sql有點新,所以我不確定如何告訴它像這樣遞歸地提取。可能嗎?

回答

2

認爲你可以用一些DataLoadOptions做吧..

+0

這樣看來,我可以。不知道這是如何影響性能的,但直到我注意到它,這個效果很好。 – captncraig 2009-12-17 04:57:00

1

對於結構,你要求可能超出LINQ。有LoadWith,但通過嘗試添加一個JOIN等工程;這對樹不起作用。

我認爲在這種情況下,調用UDF將是一個不錯的選擇(將有趣的代碼移動到數據庫)。如何走樹取決於你的版本等和確切的SQL服務器版本。例如:

CREATE FUNCTION GetWithAncestors(@id int) 
RETURNS @result TABLE (id int null, prev int null, name varchar(100) not null) 
AS 
BEGIN 
    ; 
    WITH fn (id, prev, name) 
     AS (
      SELECT tt.id, tt.prev, tt.name, 0 
      FROM TreeTest tt 
      WHERE tt.id = @id 
      UNION ALL 
      SELECT tt.id, tt.prev, tt.name 
      FROM fn 
      INNER JOIN TreeTest tt 
      ON tt.id = fn.prev 
     ) 
    INSERT @result 
    SELECT * FROM fn 
    RETURN 
END 
GO 

現在可以將UDF到您的數據上下文等

+0

LoadWith可以工作,因爲我只需要路徑上的所有節點返回到要加載的父級。它像魔術一樣。 – captncraig 2009-12-17 04:57:58