子查询转成连接查询效率更高,在此总结子查询如何转成连接查询。

等于某个条件的子查询转成连接查询

假如你发现某物品(其prod_id为DTNTR)存在问题,因此想知道生产该物品的供应商生产的其他物品是否也存在这些问题。此查询要求首先找到prod_id为DTNTR的物品的供应商,然后找出这个供应商生产的其他物品。

子查询如下形式:

SELECT prod_id,prod name
FROM products
WHERE vend_id = (SELECT vend_id
FROM products
WHERE prod_id = 'DTNTR');

可以被转换为下面这种形式的连接查询:

SELECT pl.prod_id,pl.prod name
FROM products AS pl
join products AS p2
on pl.vend_id = p2.vend_id
and p2.prod_id = 'DTNTR';

WHERE(通过匹配p1中的vend_id和p2中的vend_id)首先联结两个表,然后按第二个表中的prod_id过滤数据,返回所需的数据。

实例

student表结构如下:
数据库之子查询转化为连接查询_子查询

需求:查找和a1同一个gid的数据

子查询实现:
首先查询出a1的gid,再在student表中查询该gid的数据

select * from student 
where gid = (select gid from student where name = 'a1')

连接查询实现:

SELECT * FROM student s1
JOIN student s2
ON s1.gid = s2.gid
AND s2.`name`='a1';

结果如下:
数据库之子查询转化为连接查询_连接查询_02

包含某些条件的子查询转成连接查询

子查询如下形式:

SELECT * FROM table1
WHERE column1 IN (SELECT column2a FROM table2 WHERE column2b = value);

column1 代表 table1 中的字段,column2a 和 column2b 代表 table1 表中的字段。

可以被转换为下面这种形式的连接查询:

SELECT table1. * FROM table1 INNER JOIN table2
ON table1. column1 = table. column2a WHERE table2. column2b = value;

table1、table2连接后,使用table2的column2b字段进行过滤。

排除某些条件的子查询转成连接查询

子查询如下形式:

SELECT * FROM table1
WHERE column1 NOT IN ( SELECT column2 FROM table2);

可以被转换为下面这种形式的连接查询:

SELECT table1.* FROM table1 LEFT JOIN table2
ON table1.column1 = table2.column2 WHERE table2.column2 IS NULL;

带聚合函数的子查询转成连接查询