SQL 加入来自同一 table 的经理与他们的员工的行

SQL join manager from same table onto a row with their employees

首先,这是一个虚拟的 table 我用来显示我正在使用的数据:

employee title division email
Boss Person boss o bp@email
John Smith supervisor a jos@email
Jane Smith supervisor b jas@email
Leo Messi employee a lm@email
Amanda Kessel employee a ak@email
Derek Jeter employee b dj@email

我想得到以下信息:

employee title division email supervisor_name supervisor_email
Boss Person boss o bp@email NULL NULL
John Smith supervisor a jos@email Boss Person bp@email
Jane Smith supervisor b jas@email Boss Person bp@email
Leo Messi employee a lm@email John Smith jos@email
Amanda Kessel employee a ak@email John Smith jos@email
Derek Jeter employee b dj@email Jane Smith jas@email

我查看并尝试了以下文档:

https://www.sqltutorial.org/sql-self-join/

这里最大的区别之一是我没有任何员工或经理 ID 列可以使用。

如果您是一个部门的主管,即John Smith 是a 部门的主管,那么您管理着a 部门的所有员工。与此同时,o部门的所有主管都对老板负责,而老板对任何人都不负责。

这是迄今为止我试过的最好的代码:

select e.*, b.employee as supervisor, b.email as supervisor_email
from employees e, employees b
where b.division = e.division
and
b.title like '%supervisor%'

这让我很接近,它返回了:

employee title division email supervisor_name supervisor_email
John Smith supervisor a jos@email John Smith jos@email
Jane Smith supervisor b jas@email Jane Smith jas@email
Leo Messi employee a lm@email John Smith jos@email
Amanda Kessel employee a ak@email John Smith jos@email
Derek Jeter employee b dj@email Jane Smith jas@email

所以,它得到了正确的员工信息,但遗漏了老板记录,并将主管作为自己的主管。我想我需要某种 case 或 if 语句,但我不确定。

请告诉我这是否有意义,或者是否需要进一步说明。

您可以尝试使用 LEFT JOIN 并在两个条件下工作:

  • 当除法相同且我们正在处理关系时employee < supervisor
  • 关系为supervisor < boss

我是这样做的:

SELECT t1.*,
       t2.employee,
       t2.email
FROM      tab t1
LEFT JOIN tab t2
       ON (t1.division = t2.division AND 
           t2.title = 'supervisor' AND 
           t1.title = 'employee') 
       OR (t2.title = 'boss' AND 
           t1.title = 'supervisor') 

您会找到 SQL fiddle here

如果要更新当前 table(如果列可用),您可以执行以下操作(与@lemon 大致相同):

UPDATE testing t1 JOIN testing t2 ON t2.`division`=t1.division OR t2.division="o" SET
t1.supervisor_name=t2.`employee`, t1.supervisor_email=t2.email
WHERE (CASE
WHEN t1.`title`="employee" THEN t2.title="supervisor"
WHEN t1.`title`="supervisor" THEN t2.title="boss"
END);
SELECT * FROM testing;