C#3.0入门系列(八)-之GroupBy操作

转载 2007年09月28日 17:28:00

换一种写作风格。本节讲groupby操作。

在所有的Linq To Sql操作中,GroupBy是最难理解的一个。因为,这里和Sql的出入较大。而Group真的就能返回n多组。
打开vs,新建一工程,加入System.Data.Linq.dll的引用。把northwind数据库做个映射,添加到工程里。创建一Northwind类的对象。在这里呢,我们要做分组统计,我们要先明白什么是分组。在我们开始设计product表时,我们欲留了一列叫做CategoryID 这个字段,代表了这条记录中的产品,归属于那个类别。如图,字段的设计。

可以简单的举例,比如,当CategoryID的值为1时,就表示,对应的记录的产品是饮料类的。当它为2时,代表调味品类的。具体代表那一类,要看事先的约定。一般会专门有个表来保存这个约定。在northwind中,用Categories 表来保存这个约定。下面是catagories表中的纪录。

Categories
Product表,通过CategoryID字段关联关系。也就是说,Product表中,CategoryID字段所代表的意思,保存在Categories 表中。好了,知道分组的概念了,我们开始分类统计吧。在Linq To Sql的所有操作中,groupby算是比较难理解的一个。我要友好的提醒你注意下这里的分组所用的字段哦,这个将来是要被用做继承的哦。
我们来看下面的例子。

    var q =
        from p 
in db.Products
        group p by p.CategoryID into g
        select g;

在这里,from p in db.Products 表示从表中将对象纪录取出来。p就是每一个产品。而后面一句,group p by p.CategoryID into g表示对p进行归类,按什么归类呢,就是要按我们设定的CategoryID这个字段。而这个归类的结果,被重新命名为g,而且是必须重新命名。一旦重新命名,p的作用域就结束了,所以,最后select时,只能select g。
那有人就要问了,不重新命名可以吗?回答,可以。那你的select语句就没有了,上面语句等同与
整个查询语句返回八个组,这和我们数据库的八种产品是对应的。找到最后一个group,点开+号,我们可以看到,里面有个Key和Results View字段,其中Key为8,是数据库里对应的Seafood分类,点开Results View你会惊奇的发现,所有的Seafood都在里面。我们把代码改一下,看看dlinq究竟做了什么。

            var q = from p in db.Products
                    group p by p.CategoryID;

这是query表达式中,很少见的没有select语句的情况。我记忆中,好像只有此一种。我们还是按
    var q =
        from p in db.Products
        group p by p.CategoryID into g
        select g;
来讲解。因为这种更好理解。在T-Sql中,groupby只是用来做分组统计,计算平均值,最大值,求和等等,而在dlinq中的groupby,则发挥到了极值。我们用ToList()取到结果,来看看上面语句返回的结果。如图:


            Northwind db 
= new Northwind(ConStr);
            db.Log 
= Console.Out;
            
Query Query
            
Verification Verification

 单步调试该foreach段代码,foreach的目的是让dlinq加载数据。在console windows上,你可以看到如下输出。

SELECT [t0].[CategoryID] AS [Key]
FROM [Products] AS [t0]
GROUP BY [t0].[CategoryID]
-- Context: SqlProvider(Sql2005) Model: AttributedMetaModel Build: 2.0.20612.0

SELECT [t0].[ProductID][t0].[ProductName][t0].[SupplierID][t0].[CategoryID
][t0].[QuantityPerUnit][t0].[UnitPrice][t0].[UnitsInStock][t0].[UnitsOnO
rder
][t0].[ReorderLevel][t0].[Discontinued]
FROM [Products] AS [t0]
WHERE ((@x1 IS NULLAND ([t0].[CategoryID] IS NULL)) OR ((@x1 IS NOT NULLAND
(
[t0].[CategoryID] IS NOT NULLAND (@x1 = [t0].[CategoryID]))
-- @x1: Input Int32 (Size = 0; Prec = 0; Scale = 0) [1]
--
 Context: SqlProvider(Sql2005) Model: AttributedMetaModel Build: 2.0.20612.0

原来dlinq不仅仅是做了一个groupby操作呀,他还针对每个组,都去做了一个遍历呀。我们可以用下面的图来理解。

外面的大圈,表示全集。而这个全集被分成了若干个小的集合。每个集合就叫做g。在g集合中,包含一个系统定义的Property,叫做Key。key值实际为分类时所用字段的值。而另外一部分,是该类别中所有的product.所以,我们如果想遍历某类别中所有的纪录,要这么来做。

            var q = from p in db.Products
                    
group p by p.CategoryID into g
                    
select g;            

            foreach (
var gp in q)
            {
                
if (gp.Key == 7)
                {
                    foreach (
var p in gp)
                    { 
                     
//do something
                    }
                }
            }


 

C#3.0入门系列(九)-之GroupBy操作

C#3.0入门系列(九)-之GroupBy操作 有朋友反馈说我提供的sample不能编译。大概是版本的问题,可以到http://msdn2.microsoft.com/en-us/bb330936.a...
  • starlessnt
  • starlessnt
  • 2008年03月19日 15:46
  • 352

C#3.0入门系列(九)-之GroupBy操作

有朋友反馈说我提供的sample不能编译。大概是版本的问题,可以到http://msdn2.microsoft.com/en-us/bb330936.aspx下载for beta1的版本。本节接着讲g...
  • Night_Elf
  • Night_Elf
  • 2007年09月28日 17:30
  • 627

C#3.0介绍(八)-之GroupBy操作

换一种写作风格。本节讲groupby操作。 在所有的Linq To Sql操作中,GroupBy是最难理解的一个。因为,这里和Sql的出入较大。而Group真的就能返回n多组。 打开vs,新建...
  • iamdll
  • iamdll
  • 2014年03月21日 15:31
  • 312

cas 入门之八:cas 认证处理器-GENERIC

GENERIC(普通认证) 需要增加cas-server-support-generic-3.5.2.jar 普通认证很简单,就是将你需要认证的用户名、密码对存放在cas 服务端,一种式是直接配置...
  • zhurhyme
  • zhurhyme
  • 2014年06月26日 20:31
  • 3302

USB入门系列总结

USB是什么呢?一说USB是You SB的意思,即“你傻B”的意思。另一种说法是USB其实是美国的弟弟,因为美国叫USA,USB当然是他的弟弟了。     那么USB到底是什么呢?其实USB是通...
  • u013916997
  • u013916997
  • 2014年05月27日 17:09
  • 840

USB入门系列之一:USB概述

USB是什么呢?一说USB是You SB的意思,即“你傻B”的意思。另一种说法是USB其实是美国的弟弟,因为美国叫USA,USB当然是他的弟弟了。...
  • kevinhg
  • kevinhg
  • 2010年09月30日 23:44
  • 2116

数据结构实验之栈与队列八:栈的基本操作

Problem Description 堆栈是一种基本的数据结构。堆栈具有两种基本操作方式,push 和 pop。push一个值会将其压入栈顶,而 pop 则会将栈顶的值弹出。现在我们就来验证一...
  • shadowam
  • shadowam
  • 2017年09月27日 14:56
  • 437

C#3.0入门系列(十一)-之In, Like操作

有这么一个例子,寻找一个表中的某个字段介于某个给定的集合该怎么办?Sql写起来很简单,比如:Select * from table where id in (2,3, 4, 5)。 就是寻找id字段为...
  • Night_Elf
  • Night_Elf
  • 2007年09月28日 17:34
  • 622

C#3.0入门系列(五)-之Where操作

从本节开始,本文正式更名为C#3.0入门系列。先发布一则消息,VS2007 Beta版本已经发布咯,下载地址:http://www.microsoft.com/downloads/details.as...
  • Night_Elf
  • Night_Elf
  • 2007年09月28日 16:53
  • 642

C#3.0入门系列(六)-之OrderBy操作

本节讲orderby操作.我突然在想这么一个问题,读者会T-SQL吗?要是不知道,那我写的是不是太简单了呢?做个调查哦,不知道的举手.OrderBy操作简单的,按雇用日期排序,默认为升序       ...
  • Night_Elf
  • Night_Elf
  • 2007年09月28日 16:54
  • 675
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:C#3.0入门系列(八)-之GroupBy操作
举报原因:
原因补充:

(最多只允许输入30个字)