使用Linq创建交叉表结果

时间:2008-11-26 14:34:30

标签: linq crosstab

  

可能重复:
  Is it possible to Pivot data using LINQ?

我想知道是否可以用Linq创建交叉表样式结果。 我有一些类似于以下内容的数据:

    var list = new[]
    {
        new {GroupId = 1, Country = "UK", Value = 10},
        new {GroupId = 1, Country = "FR", Value = 12},
        new {GroupId = 1, Country = "US", Value = 18},
        new {GroupId = 2, Country = "UK", Value = 54},
        new {GroupId = 2, Country = "FR", Value = 55},
        new {GroupId = 2, Country = "UK", Value = 56}
    };

我正在尝试输出到转发器控件,如下所示:

GroupId.....UK.....FR.....US
1...........10.....12.....18
2...........54.....55.....56

它导致我的问题的动态列。任何解决方案吗?

4 个答案:

答案 0 :(得分:4)

你需要一个runtimy类来保存这些runtimy结果。 xml怎么样?

XElement result = new XElement("result",
  list.GroupBy(i => i.GroupId)
  .Select(g =>
    new XElement("Group", new XAttribute("GroupID", g.Key),
      g.Select(i => new XAttribute(i.Country, i.Value))
    )
  )
);

您是否期望每个结果单元格有多个记录?如果是这样,那里需要进行一些求和(以及更多的分组)。

(这个答案是概念证明,而不是最终结果。有几个问题需要解决,例如:列的排序,缺少单元格等等。)

答案 1 :(得分:1)

快速搜索后,您可能需要查看System.Reflection.Emit中的ModuleBuilder,TypeBuilder和FieldBuilder类。它们允许您在运行时动态创建类。除此之外,您需要对对象进行分组,然后使用从LINQ获得的分层结果执行某些操作。我不确定在运行时动态创建匿名类型字段的方法,这听起来像是需要发生的事情。

答案 2 :(得分:1)

您可以尝试使用MS提供的动态linq库。它们对于将字符串作为参数的扩展方法有许多重载。它们还有一个表达式解析器,它接受一个字符串并发出一个lambda表达式。您应该能够使用它们创建动态选择。

尽管如此,你最后会得到一个非通用的IQueryable,而不是一般的IQueryable,所以你对结果的处理有点受限,你放​​弃了一些类型的安全,但是在您的申请中可能没问题......

动态linq内容的链接是

http://weblogs.asp.net/scottgu/archive/2008/01/07/dynamic-linq-part-1-using-the-linq-dynamic-query-library.aspx

有一个链接,您可以在其中下载动态库的源代码,以及如何使用它的一些很好的插图。

答案 3 :(得分:1)

var labResults = from lab in CoreLabResults
                 where lab.Patient == 8
                 group lab by new { lab.Patient, lab.TestNo, lab.CollectedDate }
                     into labtests
                     select new
                     {
                         labtests.Key.Patient,
                         labtests.Key.TestNo,
                         labtests.Key.CollectedDate,
                         MCHC = labtests.Where(lab => lab.TestVar == "MCHC").FirstOrDefault().Result,
                         LYABS = labtests.Where(lab => lab.TestVar == "LYABS").FirstOrDefault().Result,
                         TotalTests = labtests.Count()
                     }