数据库
SQL中的GROUP BY子句
1. 基本用法
GROUP BY子句是SQL中用于对结果集进行分组的关键字。它通常与聚合函数(如SUM()、AVG()、MAX()、MIN()、COUNT()等)一起使用,以便对每个分组进行统计计算。
基本语法如下:
SELECT column1, column2, AGGREGATE_FUNCTION(column3)
FROM table_name
WHERE condition
GROUP BY column1, column2;
在这个语法中,column1和column2是你希望按它们进行分组的列,而AGGREGATE_FUNCTION(column3)是你希望对分组后的数据应用的聚合函数。
2. 作用
GROUP BY子句的主要作用是:
- 数据分组:它允许你根据一个或多个列的值将结果集中的行分成多个组。
- 聚合计算:结合聚合函数,它允许你对每个分组中的数据进行统计计算,如求和、求平均、找最大值、找最小值或计数等。
3. 示例
假设你有一个名为sales的表,其中包含以下列:salesperson(销售人员)、region(地区)和amount(销售额)。你想计算每个销售人员在不同地区的总销售额。
你可以使用以下SQL语句:
SELECT salesperson, region, SUM(amount) AS total_sales
FROM sales
GROUP BY salesperson, region;
这个查询将返回每个销售人员在不同地区的总销售额。结果集中的每一行都代表一个销售人员-地区组合的总销售额。
4. 注意事项
- 在使用
GROUP BY子句时,SELECT列表中的非聚合列必须包含在GROUP BY子句中。
- 如果
GROUP BY子句中包含多个列,那么结果集将按照这些列的组合进行分组。
- 对于包含NULL值的列,
GROUP BY会将其视为相同的值进行分组(即所有NULL值都会被分到同一个组中)。但是,在使用聚合函数时,NULL值通常会被忽略(除非使用的是COUNT()函数)。
对分组后的数据再进行过滤
HAVING子句是SQL中用于对分组后的数据进行过滤的关键字。它基于分组后的结果集进行条件筛选,而不是原始数据。因此,HAVING子句通常与GROUP BY子句一起使用。
select deptno, avg(sal) as "平均工资"
from emp
group by deptno
having avg(sal) >2000

连接查询:将两个表或两个以上的表以一定的连接条件连接起来,从中检索满足条件的数据

select top 3
from emp "E"
join dept "D"
on "E".deptno = "D".deptno
join salgrade "S"
on "E".sal between "S".losal and "S".hisal
where "D".dname not like "%A%"
order by "E".sal desc
习题1:输出每个员工的姓名 部门编号 薪水 和薪水登记
select "E".ename, "E".deptno, "E".sal, "S".grade
from emp "E"
join salgrate "S"
on "E".sal between "S".lowsal and "S".hisal
习题2:查找每个部门的编号,该部门所有员工的平均工资,平均工资的等级
select "T".deptno, "T".avg_sal, "S".grade
from
(
select deptno, avg(sal) as "avg_sal"
from emp
group by deptno
) "T"
join salgrade "S"
on "T".avg_sal between "S".losal and "S".hisal
-- 等价于
select "T".deptno, "T".avg_sal, "S".grade
from salgrade "S"
join (
select deptno, avg(sal) as "avg_sal"
from emp
group by deptno
) "T"
on "T".avg_sal between "S".losal and "S".hisal
-- 等价于
select "T".deptno, "T".avg_sal, "S".grade
from salgrade "S",(
select deptno, avg(sal) as "avg_sal"
from emp
group by deptno
) "T"
where "T".avg_sal between "S".losal and "S".hisal
习题3:求出emp表中所有领导的姓名
-- 输出emp表中所有领导的姓名
select * from emp
where empno in (select mgr from emp)
-- 输出emp表中非领导的姓名
select * from emp
where empno not in (select mgr from emp)
习题4:求出平均薪水最高的部门的编号和部门的平均工资
select deptno "部门的编号", avg(sal) "平均工资"
from emp
group by deptno
order by avg(sal) desc
习题5:把工资大于所有员工中工资最低的前3个人的姓名 工资 部门编号 部门名称 工资等级
select *
from (
select *
from emp
where sal > (select min(sal) from emp)
) "T"
join dept "D"
on "T".deptno = "D".deptno
join salgrade "S"
on "T".sal between "S".losal and "S".hisal
order by "T".sal asc
SQL嵌套查询详解
1. 定义
SQL嵌套查询(也称为子查询或内查询)是指一个查询块嵌套在另一个查询块中的查询。外层查询可以使用内层查询的结果作为条件或数据源,从而构建出更复杂的数据检索逻辑。
2. 作用
嵌套查询的主要作用是允许你使用查询结果作为其他查询的条件或数据源,从而解决一些复杂的数据检索问题。它可以帮助你从多个表中提取相关数据,并根据需要进行过滤和排序。
3. 使用场景
嵌套查询在SQL中非常常见,特别是在以下场景中:
- 数据过滤:使用子查询来过滤主查询中的结果。例如,查找工资高于公司平均工资的员工。
- 数据关联:在不需要使用JOIN操作的情况下,通过子查询来关联两个或多个表的数据。
- 计算字段:在SELECT子句中使用子查询来计算一些复杂的字段值。
4. 示例
示例1:数据过滤
假设你有一个名为employees的表,其中包含员工的姓名和工资信息。你想查找工资高于公司平均工资的员工。你可以使用以下嵌套查询:
SELECT name, salary
FROM employees
WHERE salary > (SELECT AVG(salary) FROM employees);
在这个查询中,内层查询(SELECT AVG(salary) FROM employees)计算了公司的平均工资,外层查询则选择了工资高于这个平均工资的员工。
示例2:数据关联
假设你有两个表:employees(员工)和departments(部门)。你想查找每个员工及其所在部门的名称。虽然这通常可以通过JOIN操作来实现,但你也可以使用嵌套查询:
SELECT name,
(SELECT department_name
FROM departments
WHERE departments.department_id = employees.department_id) AS department_name
FROM employees;
在这个查询中,对于employees表中的每一行,内层查询都返回了与之匹配的departments表中的部门名称。
5. 注意事项
- 性能问题:嵌套查询可能会涉及大量的数据处理,特别是当内层查询返回大量结果时。因此,在使用嵌套查询时,需要注意性能问题,并根据需要对查询进行索引和优化。
- 可读性:复杂的嵌套查询可能会降低SQL语句的可读性。因此,在编写嵌套查询时,建议尽量保持查询结构的清晰和简洁。
- 避免重复:在使用嵌套查询时,需要注意避免重复数据的产生。这可以通过使用DISTINCT关键字或适当的查询逻辑来实现。
希望这些信息能帮助你更好地理解和使用SQL中的嵌套查询。如果你有任何其他问题或需要进一步的帮助,请随时告诉我。
|