SQL错题整理总结
一、MySQL1055 - Expression #3 of SELECT list is not in GROUP BY clause and contains nonaggregated column
only_full_group_by
MySQL 其实很早就添加了 only_full_group_by 这个 sql_mode,但一直都作为可选项之一,并没有强制默认。
然而,MySQL 5.7 之后,only_full_group_by 成为 sql_mode 的默认选项之一
这就会让我们的一些惯性思维导致一系列的 SQL 错误
only_full_group_by 这个 sql_mode 的唯一要求,就是所有的 select 字段必须在 group by 字段中,否则必须出现在 SQL Aggregate 函数中,反过来却是非必须的
转载自https://www.cnblogs.com/xing-29391/p/13403617.html
因为group by后面没有包含employee_id,系统认为可能存在同样的分组中存在不同的employee_id的值。
解决方法:
1.用any_value()来包装employee_id
2.优化代码,剔除 select 语句中的多余字段,也就是不要触发 only_full_group_by。这是值得推荐的,因为这是写出好代码的必要添加之一。
二、关于sql的执行顺序问题
先筛选分组,再排序,限制。
先查找哪个表from,再where查找范围,再分组group by,之后进一步限定范围having。
然后筛选select,排序order by,限制limit。
三、where和having的区别
having查询效率比较低。
一个是先分组再加条件。一个是先加条件筛选,再进行分组。
实际开发中要在各个方面提高效率。
四、单值子查询和多值子查询
select * from departments where department_id = (select department_id
from employees
where employee_id = 150)
这种叫做单值子查询, 子查询查询的结果只有一个值。
select * from departments where department_id in (select department_id
from employees
where last_name = 'king')
多值子查询,子查询的结果是多个值。所以=变成了in。
五、查询出来的表作为新表查询数据
select sum(salary) from (select * from employees order by salary desc Limit 10)
Every derived table must have its own alias(每一个派生出来的表都必须有一个自己的别名)
后面加个e作为这个新表的别名:
select sum(salary) from (select * from employees order by salary desc Limit 10) e
六、左外连接和右外连接
左外连接:会显示左表的所有数据,如果右表没有相匹配的连接条件,就会显示为null。
select e.*,d.* from employees e right join departments d
on e.department_id=d.department_id
右外连接:会显示右表的所有数据,如果左表没有相匹配的连接条件,就会显示为null。
即:
left join (左连接):返回包括左表中的所有记录和右表中连接字段相等的记录。
right join(右连接):返回包括右表中的所有记录和左表中连接字段相等的记录。
inner join (内连接):只返回两个表中连接字段相等的行。
full join (全连接):返回左右表中所有的记录和左右表中连接字段相等的记录。