简体   繁体   English

MySQL JOIN具有多个表和SUMS

[英]MySQL JOIN with multiple tables and SUMS

I am trying to create a query that will take information out of four tables for a billing system that I am creating. 我正在尝试创建一个查询,该查询将从我正在创建的计费系统的四个表中获取信息。 I have the following tables: 我有以下表格:

Table Invoice 表发票

InvoiceID (PK)
ClientID
Date
Status
...

Table Client 表客户端

ClientID (PK)
ClientName
...

Table InvoiceItem 表InvoiceItem

ItemID (PK)
InvoiceID
Amount
...

Table Payments 表付款

PaymentID (PK)
InvoiceID
Amount
...

I need to create a query where I can access information from the Invoice table along with the client name, and the sum of all invoice items and payments associated with the invoice. 我需要创建一个查询,我可以从Invoice表中访问信息以及客户名称,以及与发票关联的所有发票项目和付款的总和。

I have tried the following: 我尝试过以下方法:

SELECT 
    Invoice.InvoiceID, 
    Invoice.`Date`, 
    Invoice.Terms, 
    Invoice.DateDue, 
    Invoice.Status, 
    Client.ClinicName, 
    SUM(InvoiceItem.Amount), 
    SUM(Payment.PaymentAmount)
FROM Invoice
JOIN (Client, InvoiceItem, Payment) ON
    (Client.ClientID=Invoice.ClientID AND
     InvoiceItem.InvoiceID=Invoice.InvoiceID AND 
     Payment.InvoiceID=Invoice.InvoiceID)

And while this kind-of works, it is multiplying the SUM() by the number of records used to get the sum (ie if there are two payments - 800,400 - It gives me (800+400)*2 -- 2400). 虽然这种方法有效,但它将SUM()乘以用于得到总和的记录数(即如果有两笔付款 - 800,400 - 它给我(800 + 400)* 2 - 2400)。 I am guessing that there is something with how I am using the join, and I have honestly never had to use join for more than one table, and I would always use GROUP BY, but I can't seem to get that to work correctly. 我猜我有一些关于我如何使用连接,我老实说从来没有使用连接多个表,我总是使用GROUP BY,但我似乎无法让它正常工作。

To make matters worse, I have been lost to the world of vb.net/MSSQL client-side programming for the past several years, so my MySQL is rather rough. 更糟糕的是,过去几年我一直迷失于vb.net/MSSQL客户端编程的世界,所以我的MySQL相当粗糙。

Your problem is that you can't aggregate over two independent tables at once in a single query. 您的问题是您无法在单个查询中一次聚合两个独立的表。 However you can do it using subqueries. 但是,您可以使用子查询来执行此操作。

SELECT Invoice.InvoiceID, Invoice.`Date`, Invoice.Terms, Invoice.DateDue, Invoice.Status, Client.ClinicName, InvoiceItemSum.SumOfAmount, PaymentSum.SumOfPaymentAmount
  FROM Invoice
  INNER JOIN Client ON Client.ClientID = Invoice.ClientID
  INNER JOIN (
    SELECT InvoiceID, SUM(Amount) AS SumOfAmount
      FROM InvoiceItem
      GROUP BY InvoiceID
  ) InvoiceItemSum ON InvoiceItemSum.InvoiceID = Invoice.InvoiceID
  INNER JOIN (
    SELECT InvoiceID, SUM(PaymentAmount) AS SumOfPaymentAmount
    FROM Payment
    GROUP BY InvoiceID
  ) PaymentSum ON PaymentSum.InvoiceID = Invoice.InvoiceID

Try this: 试试这个:

SELECT
    Invoice.InvoiceID,
    Invoice.`Date`,
    Invoice.Terms,
    Invoice.DateDue,
    Invoice.Status,
    Client.ClinicName,
    SUM(InvoiceItem.Amount),
    SUM(Payment.PaymentAmount)
FROM Invoice 
JOIN Client ON Client.ClientID=Invoice.ClientID
JOIN InvoiceItem ON InvoiceItem.InvoiceID=Invoice.InvoiceID
JOIN Payment ON Payment.InvoiceID=Invoice.InvoiceID
group by 1,2,3,4,5,6;

I did two things to your query: 我对你的查询做了两件事:

  1. Created separated joins for each of the child tables 为每个子表创建分隔的连接
  2. Added a group by , without which the sum won't work correctly (fyi, in all other databases, omitting the group by would actually result in a syntax error) 添加了一个group by ,没有该group by ,总和将无法正常工作(fyi,在所有其他数据库中,省略该组实际上会导致语法错误)

Here try this one 试试这个

SELECT  a.InvoiceID,
        a.`Date`,
        a.Terms,
        a.DateDue,
        a.Status,
        b.ClinicName,
        SUM(c.Amount),
        SUM(d.PaymentAmount)
FROM    Invoice a
            INNER JOIN Client b
                on a.ClientID = b.ClientID
            INNER JOIN InvoiceItem c
                ON c.InvoiceID = a.InvoiceID
            INNER JOIN JOIN Payment d
                ON d.InvoiceID = a.InvoiceID
GROUP BY    a.InvoiceID,
            a.`Date`,
            a.Terms,
            a.DateDue,
            a.Status,
            b.ClinicName

can you elaborate more on this? 你能详细说明一下吗?

it is multiplying the SUM() by the number of records used to get the sum (ie if there are two payments - 800,400 - It gives me (800+400)*2 -- 2400) 它将SUM()乘以用于得到总和的记录数(即如果有两笔付款 - 800,400 - 它给我(800 + 400)* 2 - 2400)

you can also achive it by "CROSS APPLY" 你还可以通过“CROSS APPLY”来实现它

SELECT Invoice.InvoiceID, Invoice.`Date`, Invoice.Terms, Invoice.DateDue, Invoice.Status, Client.ClinicName, InvoiceItemSum.SumOfAmount, PaymentSum.SumOfPaymentAmount
  FROM Invoice
  INNER JOIN Client ON Client.ClientID = Invoice.ClientID
  CROSS APPLY ( SELECT ISNULL(SUM(Amount),0) AS SumOfAmount 
                                  FROM   InvoiceItem 
                                  WHERE  InvoiceID = Invoice.InvoiceID
                                ) InvoiceItemSum 
  CROSS APPLY ( SELECT ISNULL(SUM(PaymentAmount),0) AS SumOfPaymentAmount 
                                  FROM   Payment 
                                  WHERE  InvoiceID = Invoice.InvoiceID
                                ) PaymentSum 

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM