对 4 个表的 SQL 查询:非常复杂?
我有四个表
alert:
* monitor_id
* group_id
group:
* group_id
user:
* user_id
* email
user_group:
* group_id
* user_id
是否可以仅使用 monitor_id 来获取用户的邮件? 如果是!是否可以只在一个查询中进行? 请帮助我无论是通过sql查询还是通过主义!
i have four tables
alert:
* monitor_id
* group_id
group:
* group_id
user:
* user_id
* email
user_group:
* group_id
* user_id
is it possible to have the user's mail using just the monitor_id ?
if yes! is it possible in only one query?
please help me whether by the sql query or the doctrine !
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
正确的查询:
上一个带有 Shahbaz 评论的查询。
编辑(作者:Shahbaz):为了帮助解释该命令的工作原理:
当您有两个表共享一个字段(如果您愿意,可以是一个变量)时,您可以
join
这两个表(也称为inner join
),从而产生一个更大的表,合并两个表中的数据(如果没有共享字段,您甚至可以这样做)。让我们通过一个例子来了解一下:表 People:字段:pid、pname、pjob,
其中包含条目
表工作:字段:jname,jpay,
包含条目
现在,如果您说
People join Jobs
您会得到一个包含 9 个条目的表,其中包含:字段:pid、pname、pjob、jname、jpay,
其中条目为
正如你所看到的还不是这么好的桌子!您可以使用
join
中的on
条件来提取彼此相关的信息。例如,我们可能想查看每个人的工资。因此,People.pjob 应该等于 Jobs.jname,因此,如果您说People join Jobs on People.pjob=Jobs.jname
您会得到一个表,其中包含:字段:pid、pname、pjob、jname , jpay
包含条目
请注意,Clara 的工作不存在于 Jobs 表中,因此她不存在于最终表中。
虽然
内连接
为您提供来自两个匹配表的数据,但您可能希望获取表的数据,即使另一端没有匹配的数据。这称为外连接
。在此示例中,People 外连接 Jobs
生成一个包含字段的表:pid、pname、pjob、jname、jpay,
其中条目为
null
,null
)null
,null
,null
, 'teacher', 1000)如果您只想要表即使不匹配,也要包含
outer join
的左侧,请使用left external join
(在这种情况下,将出现“Clara”行,而不是“teacher”行) ' 排)。同样,右外连接会给出右表中的行(即使不匹配),但不会给出左表中的行。最后,您必须已经知道
select
的作用,它只是返回一个表,其中包含从提供的列中选择的列(*
选择所有列)。给定的表可以只是表的名称,也可以是使用 sql 命令形成的任何其他表(使用select
命令本身创建的表(在这种情况下,请毫不犹豫地使用括号),使用加入
命令等)。如果您了解 SQL 的递归性质,您就可以创建任意复杂的命令。想象一下,表上的每个操作都会生成另一个表,您可以简单地与其他操作结合使用,就好像该表是一个简单的存储命名表一样!Right query:
Previous one with Shahbaz comments.
Edit (by Shahbaz): To help explain how the command works:
When you have two tables sharing a field (a variable if you like), you can
join
the two tables (also calledinner join
), resulting in a bigger table combining the data from the two tables (you could even do it if there are no sharing fields). Let's go through this with an example:Table People: fields: pid, pname, pjob
with entries
Table Jobs: fields: jname, jpay
with entries
Now if you say
People join Jobs
you get a table with 9 entries, having:fields: pid, pname, pjob, jname, jpay
with entries
As you can see this is not such a good table! You can use the
on
condition injoin
to extract information that are relevant to each other. For example, we may want to see the pay of each people. Therefore, the People.pjob should equal to Jobs.jname so, if you sayPeople join Jobs on People.pjob=Jobs.jname
you get a table having:fields: pid, pname, pjob, jname, jpay
with entries
Note that Clara's job didn't exist in Jobs table and thus she is not present in the final table.
While
inner join
gives you data from the two tables that match, you may want to get data of the tables even if there is no matching on the other side. This is calledouter join
. In this examplePeople outer join Jobs
yields a table havingfields: pid, pname, pjob, jname, jpay
with entries
null
,null
)null
,null
,null
, 'teacher', 1000)If you want only the table on the left side of the
outer join
to be included even if unmatched, useleft outer join
(in this case, the 'Clara' row will be present and not the 'teacher' row). Likewise,right outer join
gives rows from the right table even if unmatched, but not the left table.Finally, you must already know what
select
does, it simply returns a table with selected columns from the provided column (*
selecting all columns). The given table could be just the name of a table, or any other table formed with sql commands (tables created withselect
command itself (in which case don't hesitate to use parenthesis), tables create withjoin
command etc). If you understand this recursive nature of SQL, you can create commands as complicated as you like. Just imagine that each operation on tables, yields another table that you can simply use in conjunction with other operations as if that table was a simple stored named table!如果您想使用 Monitor_id 获取用户电子邮件,请执行以下操作:
因为从 Monitor_id 到 user.email 的路径会遍历所有表,所以您将需要所有这些联接。
只要您对连接中使用的所有字段都建立了索引(!),运行时应该会很快。
If you want to use the monitor_id to get a users email then do:
Because the path from monitor_id to user.email goes through all the tables, your will need all those joins.
As long as you have indexed (!) all fields used in the joins the runtime should be fast.
另一种方法(不使用
DISTINCT
或GROUP BY
):注意:使用关键字或保留字命名的表或字段不是一个好习惯
用户
,甚至更糟糕的组
。Another way (not using
DISTINCT
orGROUP BY
):Note: it's not good practice to have tables or fields named with keywords or reserved words like
user
and even worsegroup
.