我有两个查询都很快(20毫秒)-当我将它们与联接结合在一起时,我得到了30秒的查询,并且数据有误...什么地方出了错?
SELECT
count(profile.id),
date(profile.createdAt)
FROM profile
GROUP BY date(profile.createdAt)
ORDER BY date(profile.createdAt) DESC;
和
SELECT
count(product.id),
date(product.createdAt)
FROM product
GROUP BY date(product.createdAt)
ORDER BY date(product.createdAt) desc;
加入它们后,我得到一个非常慢的查询:
SELECT
count(profile._id),
date(profile.createdAt),
count(product._id),
date(product.createdAt)
FROM profile
INNER JOIN product
ON date(product.createdAt) = date(profile.createdAt)
GROUP BY
date(product.createdAt),
date(profile.createdAt)
ORDER BY date(product.createdAt) desc;
答案 0 :(得分:2)
当前方法的逻辑错误是由于连接而重复计算了一个或两个计数。您可以尝试在单独的子查询中进行聚合,然后加入这些子查询:
SELECT
t1.createdAt,
COALESCE(t1.profile_cnt, 0) AS profile_cnt,
COALESCE(t2.product_cnt, 0) AS product_cnt
FROM
(
SELECT DATE(createdAt) AS createdAt, COUNT(id) AS profile_cnt
FROM profile
GROUP BY DATE(createdAt)
) t1
INNER JOIN
(
SELECT DATE(createdAt) AS createdAt, COUNT(id) AS product_cnt
FROM product
GROUP BY DATE(createdAt)
) t2
ON t1.createdAt = t2.createdAt;
如果两个表都不包含相同的日期,则上述查询可能会删除某些日期。为避免这种情况,我们可以加入一个日历表,其中包含了我们希望出现在输出中的所有日期。
关于性能,您正在执行两个聚合查询的联接,因此预期不会有这种性能。另外,调用DATE
将createdAt
强制转换为纯日期是昂贵的,并且可以通过维护专用日期列来避免。
答案 1 :(得分:0)
我认为问题在于您正在加入date函数的结果,这很可能在后台进行了很多工作。该功能必须对每个表中的每个记录执行。
如果可以,请与表的主键/外键结合使用索引。