使用单个linq查询聚合来自两个表的数据

时间:2012-10-14 11:22:57

标签: c# linq

我是LINQ的新手,还没有意识到它的全部功能。

我有两张表,如下面

Links
----------------------
LinkId 
LinkTitle 
DateAdded


Articles
----------------------
ArticleId
ArticleTitle
DateAdded

我正在尝试使用单个linq查询创建结果集,该查询将输出如下所示的数据

Year
Month
NoOfLinksAdded
NoOfArticleAdded

任何帮助都将受到高度赞赏。

更新: 这就是我到目前为止所做的事情

var grouped = from p in Links 
              group p by new { month = p.DateAdded.Month,year= p.DateAdded.Year } into d 
              select new { Month = d.Key.month, Year= d.Key.year, NoOfLinksAdded = d.Count() };

1 个答案:

答案 0 :(得分:1)

以下是如何在单个查询中执行此操作,但它不是很漂亮......

var query = from n in Enumerable.Range(0, 1) //we need something to start our query from
            //shape the articles so we can append them to the links 
            let articlesShaped = from a in articles
                                 select new
                                 {
                                     IsLink = false,
                                     IsArticle = true,
                                     a.DateAdded,
                                 }
            //shape the links so we can append them to the articles
            let linksShaped = from l in links
                              select new
                              {
                                  IsLink = true,
                                  IsArticle = false,
                                  l.DateAdded,
                              }
            //append the links and articles together
            let articlesAndLinks = articlesShaped.Concat(linksShaped)
            from a in articlesAndLinks
            group a by new { a.DateAdded.Month, a.DateAdded.Year } into grouping
            select new
            {
                grouping.Key.Year,
                grouping.Key.Month,
                NoOfLinksAdded = grouping.Where(a1 => a1.IsLink).Count(),
                NoOfArticleAdded = grouping.Where(a1 => a1.IsArticle).Count(),
            };

以下是结果:

here's the output

如果将其拆分为单个步骤,则更易于维护。它也不会花费你任何性能,因为只有在你因延迟执行而遍历结果集时才会执行执行。

如果我们将代码分解为步骤,则会变成以下内容(在我看来这更好)

//shape the articles so we can append them to the links                   
var articlesShaped = from a in articles
                     select new
                     {
                         IsLink = false,
                         IsArticle = true,
                         a.DateAdded,
                     };

//shape the links so we can append them to the articles
var linksShaped = from l in links
                  select new
                  {
                      IsLink = true,
                      IsArticle = false,
                      l.DateAdded,
                  };

//append the links and articles together
var articlesAndLinks = articlesShaped.Concat(linksShaped);

var query = from a in articlesAndLinks
            //group by the month and year
            group a by new { a.DateAdded.Month, a.DateAdded.Year } into grouping
            select new
            {
                grouping.Key.Year,
                grouping.Key.Month,
                //get the number of links
                NoOfLinksAdded = grouping.Where(a1 => a1.IsLink).Count(),
                //get the number of articles
                NoOfArticleAdded = grouping.Where(a1 => a1.IsArticle).Count(),
            };

最后,这是一个完整版本,您可以运行,以便您可以看到代码在运行:

//make some test data
var links = new []
{
    new    
    {
        LinkId = 1,
        LinkTitle = "A link",
        DateAdded = new DateTime(2012, 5, 1),
    },
    new
    {
        LinkId = 2,
        LinkTitle = "Another link",
        DateAdded = new DateTime(2012, 5, 1),
    },
    new
    {
        LinkId = 3,
        LinkTitle = "A link bro!",
        DateAdded = new DateTime(2012, 6, 1),
    },
    new
    {
        LinkId = 4,
        LinkTitle = "A link dude",
        DateAdded = new DateTime(2012, 6, 1),
    },
    new
    {
        LinkId = 5,
        LinkTitle = "A link man!",
        DateAdded = new DateTime(2012, 7, 1),
    },
};
//make some test data
var articles = new []
{
    new
    {
        ArticleId = 1,
        ArticleTitle = "An article",
        DateAdded = new DateTime(2012, 6, 1),
    },
    new
    {
        ArticleId = 2,
        ArticleTitle = "An article",
        DateAdded = new DateTime(2012, 6, 1),
    },
    new
    {
        ArticleId = 3,
        ArticleTitle = "An article",
        DateAdded = new DateTime(2012, 7, 1),
    },
    new
    {
        ArticleId = 4,
        ArticleTitle = "An article",
        DateAdded = new DateTime(2012, 8, 1),
    },
};

//shape the articles so we can append them to the links                   
var articlesShaped = from a in articles
                     select new
                     {
                         IsLink = false,
                         IsArticle = true,
                         a.DateAdded,
                     };
//shape the links so we can append them to the articles
var linksShaped = from l in links
                  select new
                  {
                      IsLink = true,
                      IsArticle = false,
                      l.DateAdded,
                  };
//append the links and articles together
var articlesAndLinks = articlesShaped.Concat(linksShaped);

var query = from a in articlesAndLinks
            //group by the month and year
            group a by new { a.DateAdded.Month, a.DateAdded.Year } into grouping
            select new
            {
                grouping.Key.Year,
                grouping.Key.Month,
                //get the number of links
                NoOfLinksAdded = grouping.Where(a1 => a1.IsLink).Count(),
                //get the number of articles
                NoOfArticleAdded = grouping.Where(a1 => a1.IsArticle).Count(),
            };
相关问题