使用 JOIN 与 IN/NOT IN 以提高可读性
Posted
技术标签:
【中文标题】使用 JOIN 与 IN/NOT IN 以提高可读性【英文标题】:Usage of JOINs vs IN/NOT IN for readability 【发布时间】:2015-12-02 15:28:49 【问题描述】:让我先说这不是关于效率的问题。
假设,为了争论,我有一个包含两个表的数据库:用户和角色。
用户看起来像这样:
Username Password FirstName LastName
-------- -------- ---------- ---------
braab pass1234 Braab Himself
joe pass1257 Joe Smith
robert pass1235 Robert Irvine
kelly pass1236 Kelly Clarkson
角色如下所示:
Username Role
-------- ----
braab admin
robert customer
kelly developer
joe admin
我想查找所有具有“管理员”角色的用户的名字和姓氏。
我有两种方法来实现这一点:使用连接或使用 in 子句。
输入方法:
select
firstname, lastname
from
users
where
username in
(select
username
from
roles
where
role = 'admin'
)
加入方法:
select
user.firstname, user.lastname
from
users as user
inner join
roles as role
on
user.username = role.username
哪种方法更清楚我正在尝试查找管理员用户的名字和姓氏?有预期用途吗?对我来说,in 子句是实现上述目标的最明确的方式。
根据您对 SQL 的经验/培训,我可以看到这两种方式。我担心的是我希望其他开发人员能够理解我想要实现的目标。
【问题讨论】:
请注意,当子查询可以返回NULL
时,NOT IN
可能会很棘手。我会使用JOIN
而不是IN/NOT IN
,尤其是当子查询相关时。
一个用户可以有多个角色吗?否则最好在Users
表上添加一个字段
这两个语句不一定返回相同的东西,例如当一个用户可以拥有多个角色时
您的 JOIN 示例缺少 where role.Role = 'admin'
。至于问题:总是加入。如果您有两个以上的表,则子查询的可读性会降低。此外,效率应该对您很重要。
不能同时理解它们的人不是开发者。
【参考方案1】:
问题不在于开发人员是否能够理解代码。您应该专注于能够提供最佳性能的内容。
正如您在这个 SQL Fiddle Demo 中看到的那样,执行计划是不同的。处理哪些表的顺序不同。因为表是小索引不会成为一个因素,但这也会影响你使用什么选项。
【讨论】:
这是个问题。如果另一个开发人员必须维护我的代码,那么他们了解我在做什么很重要。性能很重要,但可读性也很重要。 *** 已经被效率问题所淹没。我想知道上面两个查询中哪一个最清楚地实现了示例中的目标。 @braab 都同样清楚,所以更像你遵循的标准。我喜欢使用更多的JOIN
而不是IN
。因为代码行更少。【参考方案2】:
FWIW,这将是我的选择。简洁易读的代码,并为不想阅读代码的人提供注释。
-- get first and last name of all users who have the 'admin' role
SELECT users.firstname
, users.lastname
FROM users
INNER JOIN roles
ON users.username = roles.username
WHERE roles.Role = 'admin'
正如我在评论中所写,一旦超过 2 个或 3 个表,JOIN 在可读性方面比 IN
子查询要好得多。
【讨论】:
以上是关于使用 JOIN 与 IN/NOT IN 以提高可读性的主要内容,如果未能解决你的问题,请参考以下文章
为什么 EXISTS(NOT EXIST) 与 JOIN(LEFT JOIN) 的性能会比 IN(NOT IN) 好
SQL in/not in/exists/not exists
oracle中in,not in和exists,not exists之间的区别