力扣解题思路——183.从不订购的客户

题目:查找从不订购的客户

Customers 表:

+-------------+---------+
| Column Name | Type    |
+-------------+---------+
| id          | int     |
| name        | varchar |
+-------------+---------+
在 SQL 中,id 是该表的主键。
该表的每一行都表示客户的 ID 和名称。

Orders 表:

+-------------+------+
| Column Name | Type |
+-------------+------+
| id          | int  |
| customerId  | int  |
+-------------+------+
在 SQL 中,id 是该表的主键。
customerId 是 Customers 表中 ID 的外键( Pandas 中的连接键)。
该表的每一行都表示订单的 ID 和订购该订单的客户的 ID。

找出所有从不点任何东西的顾客。

以 任意顺序 返回结果表。

结果格式如下所示。

示例 1:

输入:
Customers table:
+----+-------+
| id | name  |
+----+-------+
| 1  | Joe   |
| 2  | Henry |
| 3  | Sam   |
| 4  | Max   |
+----+-------+
Orders table:
+----+------------+
| id | customerId |
+----+------------+
| 1  | 3          |
| 2  | 1          |
+----+------------+
输出:
+-----------+
| Customers |
+-----------+
| Henry     |
| Max       |
+-----------+

 解题思路:

1.需要从客户表中获取客户ID,随后在订单表中查找从未出现过的客户ID。

力扣解题思路——183.从不订购的客户_第1张图片

如上图所示,可以先查询出具体的客户表ID清单,再拿去订单表筛选。

解题代码:

SELECT
    name AS Customers
FROM Customers
WHERE id NOT IN (
    SELECT
        customerId
    FROM Orders
)

在SQL中,使用“NOT IN”语句可以过滤掉某个特定的值,返回不包含该值的结果集。

需要注意一个问题,使用“NOT IN”语句时候,效率十分低下。

力扣解题思路——183.从不订购的客户_第2张图片

为什么呢?因为使用“NOT IN”语句时,可以拆成两部分看待。数据库会先执行IN,然后再执行NOT筛选。所以二者的结合效率就很低了。

其次,使用IN语句时,数据库不会使用索引,而是全表扫描,每一行都会进行对比,所以速度很慢。

优化方法1:

使用EXISTS语句提升查询速度。

EXISTS语句只用查询到匹配的数据,不用返回具体的数值,所以节省了很多数据库性能开销,提升查询速度。

其次EXISTS语句通常会使用索引来加快查询速度,这一点优于IN语句。

附上解题代码:

SELECT
    name AS Customers
FROM Customers A
WHERE NOT EXISTS(
    SELECT 
        1
    FROM Orders B
    WHERE A.ID = B.customerId
)

如下图所示,明显可以看到性能显著提升。 

力扣解题思路——183.从不订购的客户_第3张图片

优化方法2:

使用关联查询符合条件的数据。

使用客户表当主表,订单表为辅表,通过左关联后,筛选出需要的数据。

附上解题代码:

SELECT 
    A.NAME AS Customers
FROM Customers A
LEFT JOIN Orders B
ON A.ID = B.customerId
WHERE B.customerId IS NULL

执行效率如下图所示 

力扣解题思路——183.从不订购的客户_第4张图片

如果大佬们有更好的思路,欢迎留言 

你可能感兴趣的:(leetcode,数据库,算法)