以下是一个示例表:
| customer_token | created_date | orders | views |
+--------------------------------------+------------------------------+--------+-------+
| 93a03e36-83a0-494b-bd68-495f54f406ca | 10-NOV-14 14.41.09.000000000 | 1 | 0 |
| 93a03e36-83a0-494b-bd68-495f54f406ca | 20-NOV-14 14.41.47.000000000 | 0 | 1 |
| 93a03e36-83a0-494b-bd68-495f54f406ca | 26-OCT-14 16.14.30.000000000 | 2 | 0 |
| 93a03e36-83a0-494b-bd68-495f54f406ca | 11-OCT-14 16.31.11.000000000 | 0 | 2 |
在此客户数据表中,我存储了给定客户下订单或查看产品的所有日期。现在,对于报告,我想写一个查询,其中对于每个客户(auth_token),我想生成last_order_date(订单> 0的行)和last_view_date(product_views> 0的行)。
我正在寻找一个有效的查询,因为我有数百万条记录。
答案 0 :(得分:2)
select customer_token,
max(case when orders > 0 then created_date else NULL end),
max(case when views > 0 then created_date else NULL end)
from Customer
group by customer_token;
更新:此查询非常有效,因为Oracle可能只扫描一次表。分组也很有趣 - 当您使用GROUP BY时,选择列表只能包含GROUP BY或聚合函数中的列。在此查询中,计算列created_date
的MAX,但您不需要将orders
和views
放在GROUP BY中,因为它们位于MAX函数内的表达式中。这不常见。
答案 1 :(得分:0)
如果要从行中获取最大值,则需要使用MAX()聚合函数。在使用聚合函数时,最佳做法是对列进行分组。
在这种情况下,您希望按customer_token分组。这样,您将获得每组一行,并且聚合函数将为您提供该组的值。
但是,您只想查看单元格值大于0的日期,因此我建议您在MAX()函数中放置一个case语句,如下所示:
SELECT customer_token,
MAX(CASE WHEN orders > 0 THEN created_date ELSE NULL END) AS latestOrderDate,
MAX(CASE WHEN views > 0 THEN created_date ELSE NULL END) AS latestViewDate
FROM customer
GROUP BY customer_token;
只有在订单为正数且仅在视图为正时才会为您提供最大日期。如果没有该案例陈述,DBMS将不知道给您哪些群组,并且您可能会得到不正确的结果。
以下是aggregate functions的oracle参考。