我有3张桌子可以从中获取信息:
所有这些表都有'created_at'列。
我想通过created_at列抛出sql查询来获取最后30个项目, 在最坏的情况下,我将不得不从任何表中弹出30个项目,并通过PHP代码从数组中订购。
答案 0 :(得分:1)
这样的事情:
(SELECT * FROM articles)
UNION
(SELECT * FROM posts)
UNION
(SELECT * FROM pictures)
ORDER BY created_at DESC
LIMIT 30
这是未经测试的,但应该有效。确保将“*”更改为您正在使用的任何字段。
答案 1 :(得分:1)
以过去的答案为基础,并在此处添加一些优化:
SELECT created_at, tbl, id, name, author_id FROM
(SELECT created_at, "articles" as tbl, id, name, author_id
FROM `articles` ORDER BY created_at DESC LIMIT 30
UNION
SELECT created_at, "posts" as tbl, id, name, author_id
FROM `posts` ORDER BY created_at DESC LIMIT 30
UNION
SELECT created_at, "pictures" as tbl, id, name, author_id
FROM `pictures` ORDER BY created_at DESC LIMIT 30
)
ORDER BY created_at DESC LIMIT 30;
FWIW - 这是未经测试的,可能包含愚蠢的错误。
我首先假设created_at已在所有三个表上编入索引。 我还要限制每个表只返回'最后30个项',所以我们没有订购一个可能很大的派生表(我们无法索引)。
因此,派生表上的最终'order by'保证订购< = 90行 比订购3个表的总联合要好得多。
答案 2 :(得分:0)
类似的东西:
SELECT * FROM
(SELECT * FROM articles UNION SELECT * FROM posts UNION SELECT * FROM pictures)
ORDER BY created_at DESC LIMIT 30
几乎可以肯定,您需要将*
替换为您要选择的两个表共有的字段列表(例如,ID),并且可能需要识别它的对象类型(例如,{ {1}})
小心放置SELECT a, b, 'article' AS item_type
条款的位置。理想情况下,您可以在每个内部选择上放置一个以限制其中包含的对象,而不是在外部放置一个必须等待整个WHERE
操作首先执行的WHERE
。{ / p>
答案 3 :(得分:0)
我会选择:
Select top 30 * from
(select acticles.created_at, ID
from articles
UNION
select posts.created_at, ID
from posts
UNION
select pictures.created_at, ID
from pictures
ORDER BY 1)