sql之表连接和group by +组函数的分析
2013-11-20 14:41
162 查看
1、首先我们来先看一个简单的例子:
有[Sales.Orders]订单表和[Sales.Customers]顾客表,表的机构如下
![](http://images.cnitblog.com/blog/579331/201311/20141753-b93a195d2333410d9687a79d1073df3a.jpg)
![](http://images.cnitblog.com/blog/579331/201311/20141820-6df00ba708c2403396279e90de6005f3.jpg)
业务要求:筛选 来自“按时打算”国家的用户以及所下的订单数
这样简单的查询,大家都能够看明白,就不再解释,就是使用了一个 内连接,和group by 进行分组,然后对分组后的数据进行 使用组函数Count进行求和
2、才是要讲解的重点:三张表连接的 组函数的使用问题
这里要增加一张表:[Sales.OrderDetails]订单详细表:表结构:
![](http://images.cnitblog.com/blog/579331/201311/20142904-2ecfb0050b274879ab086a1f5df5b472.jpg)
业务要求:查询出每个用户 买了 多少件商品 下过多少订单
说明:关于外连接和内连接的区别就不再说明,我在以前的文章里面已经进行说明了。现在说明为什么原来的 cunnt(*)是不对了,因为客户表 1对多 订单表,订单表 1对多 订单详细表。所以就要注意了,连接之后就会根据 最多的,最底层的 订单详细表的数量为基准,产生 一张连接表,所以这个时候就会有很多的订单的编号是重复的,所以直接求和就会有很多重复的数据也进行求和了,所以是错的。应该对 消除重复的订单编号 进行求和。
有[Sales.Orders]订单表和[Sales.Customers]顾客表,表的机构如下
![](http://images.cnitblog.com/blog/579331/201311/20141753-b93a195d2333410d9687a79d1073df3a.jpg)
![](http://images.cnitblog.com/blog/579331/201311/20141820-6df00ba708c2403396279e90de6005f3.jpg)
业务要求:筛选 来自“按时打算”国家的用户以及所下的订单数
select o.custid,COUNT(*) as '订单数' from [Sales.Orders] o inner join [Sales.Customers] c on o.custid=c.custid where c.country='按时打算' group by o.custid;
这样简单的查询,大家都能够看明白,就不再解释,就是使用了一个 内连接,和group by 进行分组,然后对分组后的数据进行 使用组函数Count进行求和
2、才是要讲解的重点:三张表连接的 组函数的使用问题
这里要增加一张表:[Sales.OrderDetails]订单详细表:表结构:
![](http://images.cnitblog.com/blog/579331/201311/20142904-2ecfb0050b274879ab086a1f5df5b472.jpg)
业务要求:查询出每个用户 买了 多少件商品 下过多少订单
select o.custid, --SUM(qty):下面 用case是因为:组函数对 null 值不进行处理,所以含有求和之后返回null,而不是0 case when SUM(qty) is null then '0' else SUM(qty) end as '商品数量',-- count(*),(比原来的订单数 多)--:相求订单数量,这是错的,因为三张表 关联,这个时候,并不是级联的 一对多的关系,况且,订单表 处在 一对多的 关系的 中间 的位置 count( distinct o.orderid) as '订单数'--将 重复的 订单 删除掉,这样求出的数量就是 对的了 from [Sales.OrderDetails] od right join [Sales.Orders] o on od.orderid=o.orderid inner join [Sales.Customers] c on o.custid=c.custid group by o.custid
说明:关于外连接和内连接的区别就不再说明,我在以前的文章里面已经进行说明了。现在说明为什么原来的 cunnt(*)是不对了,因为客户表 1对多 订单表,订单表 1对多 订单详细表。所以就要注意了,连接之后就会根据 最多的,最底层的 订单详细表的数量为基准,产生 一张连接表,所以这个时候就会有很多的订单的编号是重复的,所以直接求和就会有很多重复的数据也进行求和了,所以是错的。应该对 消除重复的订单编号 进行求和。
相关文章推荐
- SQL多表连接查询实例分析(详细图文)
- sql语句的优化分析之一查询语句中左连接和函数效率分析比较
- asp.net使用LINQ to SQL连接数据库及SQL操作语句用法分析
- SQL server安装及连接时出错分析及解决方案……
- SQL优化经典----利用分析函数优化自连接
- SQL 连接操作 及 查询分析
- shinx索引部分源码分析——过程:连接到CSphSource对应的sql数据源,通过fetch row取其中一行,然后解析出field,分词,获得wordhit,最后再加入到CSphSource的Hits里
- 深入sql数据连接时的一些问题分析
- 深入sql数据连接时的一些问题分析
- 《卸甲笔记》-PostgreSQL和Oracle的SQL差异分析之一:外连接
- PL/SQL Developer(32位)如何连接64位的Oracle分析
- 数据库监听与PL/SQL连接故障分析
- asp.net使用LINQ to SQL连接数据库及SQL操作语句用法分析
- sqlplus连接oracle失败分析和解决
- SQL连接查询及性能分析
- ORACLE SQL语句优化技术分析
- sql数据连接时的一些小问题
- SQL语句中Where后面最多能连接多少个条件
- 深入理解SQL的四种连接-左外连接、右外连接、内连接、全连接
- pl/sql通过修改配置文件的方式实现数据库的连接