对嵌套的外键关系执行SUM

时间:2012-07-03 21:56:02

标签: mysql sql sqlite postgresql

我有一些大致相同的表格:

Client:
   id
   name

Employee 
   id 
   name

Email
   id
   to : Client [ForeignKey]
   from : Employee [ForeignKey]

EmailStats (Tracks the stats for a particular single email)
   id
   email : Email [OneToOne]
   curse_words : 10

我想做什么:我想要提取所有已向一个客户写入至少一封电子邮件的员工,以及他们的次数他们在发送给该单个客户的任何电子邮件中都受到了诅咒,即特定的Client返回

[
    ('name' : 'Paul', 'total_curses' : 255),
    ('name' : 'Mary', 'total_curses' : 10),
]

我尝试了什么:

我对SQL的理解非常薄弱,因为我习惯使用ORM。我无法理解Employees的正常检索如何链接到诅咒词的计数中。这就是我所做的(善良!):

SELECT DISTINCT (
    SELECT SUM(EmailStats.curse_words)
    FROM EmailStats
    INNER JOIN (
      SELECT Email.id
      FROM Email
      INNER JOIN Employee
          ON Email.from = Employee.id
      WHERE Email.to = 5 // Assuming 5 is the client's id
    ) filtered_emails ON EmailStats.email = filtered_emails.id                
) AS 'total_curses', Employee.name
FROM Employee
INNER JOIN Email
   ON  Email.from = Employee.id 
WHERE Email.to = 5 // Assuming 5 is the client's id
ORDER_BY 'total_curses'

这不起作用 - 它似乎获取了正确的Employees(已发送到Client的人)但是诅咒计数似乎是所有电子邮件的总数{{1而不仅仅是Client的那些诅咒。

我有一种感觉,我在这里严重误解了一些东西,所以如果有人能提供一个如何成功实现这一点的例子,我会感激一些指点。

2 个答案:

答案 0 :(得分:3)

您想对加入表格的结果进行分组:

SELECT   Employee.name, SUM(EmailStats.curse_words) total_curses
FROM     Email
  JOIN EmailStats ON EmailStats.email = Email.id
  JOIN Employee   ON Employee.id      = Email.from
WHERE    Email.to = 5
GROUP BY Employee.id
ORDER BY total_curses DESC

答案 1 :(得分:2)

SELECT em.name, sum(s.curse_words) AS total_curses
FROM   employee em
JOIN   email e ON e.from = em.id
LEFT   JOIN emailstats s ON s.email = e.id
WHERE  e.to = $the_one_client
GROUP  BY em.name
ORDER  BY total_curses DESC;

我使用LEFT JOIN来确保,因为似乎没有保证,emailstats中的匹配行实际存在。