2009-08-04 68 views
1

說我有這種格式的DataTable:LINQ加入,合併,與父母捲起

id | key1 | key2 | data1 | data2 | parentID 
10 | AA | one | 10.3 | 0.3 | -1 
10 | AA | two | 20.1 | 16.2 | -1 
10 | BB | one | -5.9 | 30.1 | -1 
20 | AA | one | 403.1 | -20.4 | 10 
30 | AA | one | 121.5 | 210.3 | -1 

和第二數據表,如下所示:

id | data 
10 | 5500 
20 | -3000 
30 | 500 

我想要做的將數據集中在「id」級別,將第二個表的「data」字段添加到第一個「data1」網絡中,然後將「data2」加入其自身。我想出瞭如何做到這一點,但我堅持的是這樣的:我想要將「parentID」!= -1的任何數據添加到它的父項中。因此,上述數據的輸出應該

id | data1 | data2 
10 | 2927.6 | 26.2 
30 | 621.5 | 210.3 

是有一個有效的方式來做到這一點?

編輯:代碼示例

 DataTable dt1 = new DataTable(); 
     dt1.Columns.Add("id", typeof(int)); 
     dt1.Columns.Add("key1", typeof(string)); 
     dt1.Columns.Add("key2", typeof(string)); 
     dt1.Columns.Add("data1", typeof(double)); 
     dt1.Columns.Add("data2", typeof(double)); 
     dt1.Columns.Add("parentID", typeof(int)); 

     DataTable dt2 = new DataTable(); 
     dt2.Columns.Add("id", typeof(int)); 
     dt2.Columns.Add("data", typeof(double)); 

     dt1.Rows.Add(new object[] { 10, "AA", "one", 10.3, 0.3, -1 }); 
     dt1.Rows.Add(new object[] { 10, "AA", "two", 20.1, 16.2, -1 }); 
     dt1.Rows.Add(new object[] { 10, "BB", "one", -5.9, 30.1, -1 }); 
     dt1.Rows.Add(new object[] { 20, "AA", "one", 403.1, -20.4, 10 }); 
     dt1.Rows.Add(new object[] { 30, "AA", "one", 121.5, 210.3, -1 }); 

     dt2.Rows.Add(new object[] { 10, 5500 }); 
     dt2.Rows.Add(new object[] { 20, -3000 }); 
     dt2.Rows.Add(new object[] { 30, 500 }); 

     var groups = dt1.AsEnumerable() 
         .GroupBy(e => e["id"]) 
         .Select(e => new 
            { 
             id = e.Key, 
             net_data1 = e.Sum(w => (double)w["data1"]), 
             net_data2 = e.Sum(w => (double)w["data2"]) 
            }) 
         .GroupJoin(dt2.AsEnumerable(), e1 => e1.id, e2 => e2["id"], 
            (a1, a2) => new 
               { 
                id = a1.id, 
                net_data1 = a1.net_data1 + a2.Sum(w => (double)w["data"]), 
                net_data2 = a1.net_data2 
               }); 
+1

你爲什麼不張貼你有已有的代碼... – 2009-08-04 15:23:23

回答

0

不幸的是,SQL(以及通過擴展,LINQ)不是非常適合於遞歸。 parentID列可以深入多層次嗎?就像這樣:

ID  Parent 
------------------ 
10  -1 
20  10 
30  10 
40  20 

如果您想從ID 40追溯的步驟達ID是10,那麼你就應該放棄一個SQL/LINQ的做法,只是做在代碼。

+0

沒了,在這種情況下,它只是一個級別。 – toasteroven 2009-08-04 15:44:01

0

這聽起來像是一個很好的使用組連接。這樣的事情可能工作(雖然它是完全未經測試):

var items = from parent in context.dataTable 
      join child in context.dataTable on parent.id equals child.parentID into children 
      where parent.parentID == -1 
      select new { id = parent.id, 
         data1 = (parent.data1 + children.Sum(c => c.data1)), 
         data2 = (parent.data2 + children.Sum(c => c.data2)) }; 
+0

我想我明白你要做什麼的邏輯,我會嘗試一下。 在一個側面說明,我設法得到我想要的一種方法是添加相同的「parentID」列到第二個DataTable,並且如果「id」!= -1,則按groupID加入「parentID」...沒有我想要的那麼優雅,但它有效。 – toasteroven 2009-08-04 16:08:10