多表查询
笛卡尔集
语法:
select name,boyName from beauty,boys;
笛卡尔集会在下面条件下产生
– 省略连接条件
– 连接条件无效
– 所有表中的所有行互相连接
• 为了避免笛卡尔集, 可以在 WHERE 加入有 效的连接条件。
等值/连接 连接
使用连接在多个表中查询数据
• 在 WHERE 子句中写入连接条件。
• 在表中有相同列时,在列名之前加上表名前缀
区分重复的列名
• 在不同表中具有相同列名的列可以用表的别名加以区分。
• 如果使用了表别名,则在select语句中需要使用表别名代替表名
• 表别名最多支持32个字符长度,但建议越少越好
表的别名
• 使用别名可以简化查询。
• 使用表名前缀可以提高执行效率。
连接多个表
• 连接 n个表,至少需要 n-1个连接条件。 例如:连接三个表,至少需要两个连接条件。
连接查询案例
/*
含义:又称多表查询,当查询的字段来自于多个表时,就会用到连接查询
笛卡尔乘积现象:表1 有m行,表2有n行,结果=m*n行
发生原因:没有有效的连接条件
如何避免:添加有效的连接条件
分类:
按年代分类:
sql92标准:仅仅支持内连接
sql99标准【推荐】:支持内连接+外连接(左外和右外)+交叉连接
按功能分类:
内连接:
等值连接
非等值连接
自连接
外连接:
左外连接
右外连接
全外连接
交叉连接
*/
SELECT 表1列,表2列 FROM 表1,表2 WHERE 表2.列=表1.id;
#一、sql92标准
SELECT 列,列 FROM 表1,表2 WHERE 表2.'列'=表1.'列';
#三表连接
#案例:查询员工名、部门名和所在的城市
SELECT last_name,department_name,city
FROM t_mysql_employees e,t_mysql_departments d,t_mysql_locations l
WHERE e.`department_id`=d.`department_id`
AND d.`location_id`=l.`location_id`
AND city LIKE 's%'
ORDER BY department_name DESC;
join链接
分类
– 内连接 [inner] join on
– 外连接
• 左外连接 left [outer] join on
• 右外连接 right [outer] join on
使用ON 子句创建连接
• 自然连接中是以具有相同名字的列为连接条件的。
• 可以使用 ON 子句指定额外的连接条件。
• 这个连接条件是与其它条件分开的。
• ON 子句使语句具有更高的易读性。
语法:
#二、sql99语法
select 列 from 表1 别名 连接类型
join 表2 别名 on 连接条件
where 筛选条件
group by 分组列
having 筛选条件
order by 排序列表
内连接
select 查询列表 from 表1 别名
inner join 表2 别名
on 连接条件;
外连接
应用场景:用于查询一个表中有,另一个表没有的记录
1、外连接的查询结果为主表中的所有记录
从表中有和它匹配的,则显示匹配值,没有则显示null
2、左外连接,left join左边的是主表
右外连接,right join右边的是主表
3、全外连接=内连接结果+表1中有表2没有+表2有表1没有的
#左外
SELECT b.*,bo.* FROM boys bo
LEFT OUTER JOIN beauty b
ON b.boyfriend_id = bo.id
WHERE b.id IS NULL;
#右外
SELECT d.*,e.employee_id FROM employees e
RIGHT OUTER JOIN t_mysql_departments d
ON d.department_id = e.department_id
WHERE e.employee_id IS NULL;
#全外
SELECT b.*,bo.* FROM beauty b
FULL OUTER JOIN boys bo
ON b.boyfriend_id= bo.id;
#交叉连接
SELECT b.*,bo.* FROM beauty b
CROSS JOIN boys bo;
常见函数
字符函数
数字函数
日期函数
子查询
分类
按子查询出现的位置:
select后面:
仅仅支持标量子查询
from后面:
支持表子查询
where或having后面:★
标量子查询(单行) √
列子查询 (多行) √
行子查询
exists后面(相关子查询)
表子查询
按结果集的行列数不同:
标量子查询(结果集只有一行一列)
列子查询(结果集只有一列多行)
行子查询(结果集有一行多列)
表子查询(结果集一般为多行多列)
代码
#where或having后面
SELECT last_name,job_id,salary FROM t_mysql_employees
WHERE job_id = (
SELECT job_id FROM t_mysql_employees
WHERE employee_id = 141
) AND salary>(
SELECT salary FROM t_mysql_employees
WHERE employee_id = 143
);
#from后面
SELECT AVG(salary),department_id FROM t_mysql_employees
GROUP BY department_id
HAVING AVG(salary)=(
SELECT MIN(ag) FROM (
SELECT AVG(salary) ag,department_id
FROM t_mysql_employees
GROUP BY department_id
) ag_dep
);
分页查询
语法
select 查询列表 from 表
join type join 表2
on 连接条件
where 筛选条件
group by 分组字段
having 分组后的筛选
order by 排序的字段
limit 起始下标,显示条数;
特点
①limit语句放在查询语句的最后
②公式
要显示的页数 page,每页的条目数size
select 查询列表 from 表
limit (page-1)*size,size;