我正在尝试从数据库导出数据,并使用“orders”表加入“customers”表。这是一对多关系,客户可以拥有多个订单。我正在尝试编写一个查询,该查询返回customers表中的基本客户信息 - email_address,firstname,lastname,但也包括他们放置的最后一个订单的日期。
customers as c
- customer_id
- firstname
- lastname
- email_address
orders as o
- orders_id
- customers_id
- purchase_date
我希望结果为每位客户返回一个结果,其中购买日期是客户最后一次购买。
c.firstname,c.lastname,c.email_address,o.purchase_date
使这种情况发生的正确SQL语法是什么?
答案 0 :(得分:1)
select c.*, o.LastOrderDate
from customers c
LEFT JOIN
(select customers_id, max(purchase_date) as LastOrderDate
from orders
group by customers_id) o on o.customers_id=c.customers_id
将获得所有客户以及最后一个订单的日期(如果存在)。
答案 1 :(得分:0)
怎么样:
SELECT c.firstname, c.lastname, c.email_address, MAX(o.purchase_date)
FROM customers AS c
JOIN orders AS o ON o.customers_id = c.customer_id
GROUP BY c.firstname, c.lastname, c.email_address
这仅列出至少下过一个订单的客户。如果您想要所有客户,那么您应该能够使用LEFT JOIN而不是简单的(INNER)JOIN,如图所示。
答案 2 :(得分:0)
这将返回所有客户,无论他们是否有任何订单:
SQL> select c.name
2 , c.email_address
3 , ( select max (o.order_date) from orders o
4 where o.customer_no = c.customer_no )as last_order
5 from customers c
6 /
NAME EMAIL_ADDRESS LAST_ORDE
-------------------- ------------------------- ---------
ACME Industries info@acme.com 07-APR-10
Tyrell Corporation accounts@tyrellcorp.com 26-MAR-10
Lorax Textiles Co the.lorax@hotmail.com
SQL>
相当于LEFT OUTER JOIN:
SQL> select c.name
2 , c.email_address
3 , o.last_order_date
4 from customers c
5 left join ( select o.customer_no
6 , max (o.order_date) as last_order_date
7 from orders o
8 group by o.customer_no ) o
9 on o.customer_no = c.customer_no
10 /
NAME EMAIL_ADDRESS LAST_ORDE
-------------------- ------------------------- ---------
ACME Industries info@acme.com 07-APR-10
Tyrell Corporation accounts@tyrellcorp.com 26-MAR-10
Lorax Textiles Co the.lorax@hotmail.com
SQL>
RIGHT OUTER JOIN只返回带有订单的客户的行。假设一个订单必须有一个客户(即强制执行的外键),那么它将与INNER JOIN相同。
如果您的数据库风格支持分析函数,那么RANK()提供了另一种解决方法......
SQL> select name
2 , email_address
3 , order_date
4 from (
5 select c.name
6 , c.email_address
7 , o.order_date
8 , rank () over (partition by c.customer_no
9 order by o.order_date desc ) as rnk
10 from customers c
11 join orders o
12 on ( o.customer_no = c.customer_no)
13 )
14 where rnk = 1
15 /
NAME EMAIL_ADDRESS ORDER_DAT
-------------------- ------------------------- ---------
ACME Industries info@acme.com 07-APR-10
Tyrell Corporation accounts@tyrellcorp.com 26-MAR-10
SQL>
这也仅返回带有订单的客户的行。