一、多表查询问题:
笛卡尔积问题;
解决办法:
在where语句中加入有效的连接条件;一般是等值连接。
注意:连接几张表,至少需要n-1个连接条件。
二、多表查询分类:
区别:区别在于语法或查询条件有区别。
(1)内连接查询:
1.隐式内连接查询
2.显示内连接查询
(2)外连接查询:
1.左外连接查询
2.右外连接查询
3.全外连接查询
三、内连接查询:
3.1、隐式内连接查询:
语法:
SELECT 字段1, 字段2, …
FROM 表1名称 , 表2名称, …
WHERE 条件(S)/消除笛卡尔积连接
[ORDER BY 排序字段 [ASC|DESC] [, 排序字段 [ASC|DESC], …]];
注意:
在 WHERE 子句中写入连接条件;
当多个表中有重名列时,必须在列的名字前加上表名作为前缀或者表的别名(使用别名更简单,性能更高);
等值连接是连接操作中最常见的一种,通常是在存在主外键约束条件的多表上建立的,连接条件中的两个字段通过等号建立等值关系。
3.2、显式内连接查询:
语法:
SELECT 字段1, 字段2, …
FROM 表1名称 JOIN 表2名称
ON 表1名称.条件 =表2名称.条件
WHERE 条件
多个表时:
SELECT 字段1, 字段2, …
FROM 表1名称
JOIN 表2名称
ON 表1名称.条件 =表2名称.条件
JOIN
ON 表3名称.条件=.......
WHERE 条件
隐式与显式两者区别:
显示内连接查询:查询的结果和隐式内连接一模一样。区别在于:
显示内连接可以看到 JOIN;
消除笛卡尔积条件使用写在 ON 子句。
四、外连接查询:
4.1、左外连接查询 (left)
语法:
SELECT 字段1, 字段2, …
FROM 表1名称 LEFT JOIN 表2名称
ON 表1名称.条件 =表2名称.条件
WHERE 条件
过程是:
过程是:
先查询出join左边表的全部数据,
join右表不匹配的数据,使用null来填充数据。
即:表1 中的条件等于表2中的条件;表1与表1消除笛卡尔条件的字段有一个为null或者不相等时,那么先将右表中表1的数据全部查询出来,将左表表2中符合的迪卡尔条件的字 段的数据显示出来。不符合以Null填充;
而使用内连接时则两表时笛卡尔条件不相等的字段的数据都不显示出来。
4.2、右外连接查询 (RIGHT)
语法:
SELECT 字段1, 字段2, …
FROM 表1名称 RIGHT JOIN 表2名称
ON 表1名称.条件 =表2名称.条件
WHERE 条件
过程是:
查询出 JOIN 右边表的全部数据查询出来,JOIN 左边的表不匹配的数据使用 NULL 来填充数据。
五、分组函数:
5.1、函数分类
单行函数:将每条数据进行独立的计算,然后每条数据得到一条结果;
结数据中有多少条数据就会执行多少次单行函数,对应多少条结果,如日期函数.
多行函数:多条数据同时计算,最终得到一条结果数据。也成为聚集函数、分组函数,主要用于完成一些统计功能等等。
5.2、多行函数
COUNT():查询表中的数据记录;
AVG():求出平均值;
SUM():求和;
MAX():求出最大值;
MIN():求出最小值。
注意:
统计函数忽略空值,可以使用 IFNULL, 因为是 NULL 不会影响汇总值,但会影响汇总数量;
例子: count(IFNULL(字段,0))
不能在 where 语句中使用分组函数。
例子 select * from student where count(*)>0
5.3、单行函数
日期函数:
NOW():获取当前时间;
DAY(date):获取日期中的天数,范围是从 1 到 31;
HOUR(time):返回 time 对应的小时数,范围是从 0 到 23;
MINUTE(time):返回 time 对应的分钟数,范围是从 0 到 59;
MONTH(date):返回 date 对应的月份,范围时从 1 到 12;
YEAR(date):返回 date 对应的年份,范围是从 1000 到 9999;
LAST_DAY(date):获取一个日期或日期时间值,返回该月最后一天对应的值。
日期转换为字符串:
%Y: 年份,数字形式,4位数
%m: 月份,数字形式(00..12)
%d: 该月日期,数字形式(00..31)
%H: 小时(00..23)
%s: 秒(00..59)
例子:
SELECT DATE_FORMAT(NOW(), '%Y-%m-%d')
六、分组查询:
6.1、分组查询语法(GROUP BY)
SELECT 字段1, 字段2, …
FROM 表名称1 , [表名称2 , …]
WHERE 条件(s)
GROUP BY 分组字段1 [, 分组字段2 ,…]-------------------------->GROUP BY 必须写在where之后
ORDER BY 排序字段 ASC | DESC [, 排序字段 ASC | DESC];
效果:
使用 GROUP BY 子句将表分成小组;
结果集隐式按升序排列,如果需要改变排序方式可以使用 ORDER BY 子句。
6.2、分组查询注意:
(1).GROUP BY 必须写在where之后;
(2).SELECT 子句出现的字段,要不在统计函数中,要不出现在 GROUP BY 子句中,否则不合理(整体与个体);
(3).在GROUP BY 子句中出现的字段,可以不出现在 SELECT 列表中;
(4).统计函数可以单独使用,SQL 中可以没有 GROUP BY 子句;
(5).在 GROUP BY 子句中,可以按单列进行分组,也可以在多列上进行分组,多列分组就是按照多个字段的组合进行分组,最终的结果也会按照分组字段进行排序显示。
6.3、分组限定:
对分组查询完之后的数据结果不满意,还想过滤一次。
注意:若一个SOL 语句同时出现 WHERE 、GROUP BY 、 HAVING ,where 是分组之前过滤,是分组后过滤HAVING
注意:
(1)、不能在 WHERE 子句中对分组限定,限制组须使用 HAVING 子句;
(2)、不能在 WHERE 子句中使用统计函数,而在 HAVING 子句可使用统计函数。
例子:查询年龄大于20的学生及平均年龄。
select sex ,avg(sin) s from student GROUP BY sex HAVING a>18 ---and ......
多个条件时
七、子查询:
7.1、定义和作用
子查询指的就是在一个查询之中嵌套了其他的若干查询。
在使用 SELECT 语句查询数据时,有时候会遇到这样的情况,在 WHERE 查询条件中的限制条件不是一个确定的值,而是一个来自于另一个查询的结果
7.2、语法:
SELECT 字段1
FROM 表1
WHERE 条件表达式 (SELECt 字段2 FROM 表2)
注意:
(1).子查询一般出现在 FROM 和 WHERE 子句中;
(2).子查询要使用圆括号括起来;
(3).将子查询放在比较运算符的右边(增强可读性);
(4).子查询在主查询前执行一次,主查询使用子查询的结果;但不宜嵌套过多。
7.3、分类
单行单列:只包含一个字段的查询,返回的查询结果也只包含一行数据;
多行单列:只包含了一个字段,但返回的查询结果可能多行或者零行;
多行多列:包含多个字段的返回,查询结果可能是单行或者多行,好比是一张表。
7.4、单行单列
一般用于 WHERE 之后的子查询,子查询结果是一行一列记录。
使用单行记录比较运算符:=、>、>=、<、<=、<>。
7.5、多行单列
一般也用于 WHERE 子句中,子查询结果只有一列,但是有多行。使用多行比较运算符:
IN :与列表中的任意一个值相等
ANY :与子查询返回的任意一个值比较
=ANY :此时和 IN 操作符相同
>ANY :大于子查询中最小的数据
<ANY :小于子查询中最大的数据
ALL :与子查询返回的每一个值比较
>ALL :大于子查询中最大的数据
<ALL :小于子查询中最小的数据
7.6、多行多列
子查询的结果是多行多列,一般会把子查询返回的结果当成一个临时表,接着在临时表上继续查询或者连接查询;
注意:多行多列的子查询返回的结果必须要设置一个临时表名。
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/188572.html