[英]How to join tables with union ? mysql
我有两个表:
我想运行此查询:
SELECT name, talias.*
FROM
(SELECT business.bussName as name history.*
FROM history
INNER JOIN business on history.bussID = business.bussID
WHERE history.activity = 'Insert' OR history.activity = 'Update'
UNION
SELECT name as Null, history.*
FROM history
WHERE history.activity = 'Delete'
) as talias
WHERE 1
order by talias.date DESC
LIMIT $fetch,20
这个查询需要13秒钟,我认为问题在于Mysql联接了历史和业务表中的所有行! 虽然它应该只加入20行!
我该如何解决?
尝试这个:
SELECT h.*
FROM history AS h
WHERE (h.activity IN ('Insert', 'Update')
AND EXISTS (SELECT * FROM business AS b WHERE b.bussID = h.bussID))
OR h.activity = 'Delete'
ORDER BY h.date DESC
LIMIT $fetch, 20
为了使ORDER BY
和LIMIT
有效,请确保您在history.date
上有一个索引。
如果我理解正确,那么您希望deleted
历史记录中所有deleted
活动的行,以及所有那些活动为“插入”或“更新” 并且在业务表中有对应行的行。
我不知道这是否会比您的查询更快-您将需要检查执行计划以验证这一点。
SELECT *
FROM history
where activity = 'Delete'
or ( activity in ('Insert','Update')
AND exists (select 1
from business
where history.bussID = business.bussID))
order by `date` DESC
LIMIT $fetch,20
编辑 (问题更改后)
如果确实需要业务表中的列,则用外部联接替换union
可以提高性能。
但是说实话,我没想到。 MySQL优化器不是很聪明,如果外部联接实际上是使用某种联合实现的,我也不会感到惊讶。 同样,只有您可以通过查看执行计划来进行测试。
SELECT h.*,
b.bussName as name
FROM history
LEFT JOIN business b
ON h.bussID = b.bussID
AND h.activity in ('Insert','Update')
WHERE h.activity in ('Delete', 'Insert','Update')
ORDER BY h.`date` DESC
LIMIT $fetch,20
顺便说一句: date
是一个可怕的列名称。 首先是因为它是保留字,其次(也是更重要的原因)是因为它没有记录任何内容。 那是“创建日期”吗? “删除日期”? “到期日”? 还有其他日期吗?
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.