我正在尝试制作一个简单的讨论板,因此我需要主题标题及其作者以及主题最后帖子的作者。
到目前为止我已经有了这个
SELECT
`t`.`id`,
`t`.`title`,
`t`.`date` as theme_date,
`u`.`id` as user_id,
`u`.`username` as user_username,
COUNT(p.id) as count_posts,
SUBSTRING_INDEX(GROUP_CONCAT(`p`.`id` ORDER BY `p`.`id` DESC SEPARATOR "| " ), "| ", 1) as last_post_id,
SUBSTRING_INDEX(GROUP_CONCAT(`p`.`date` ORDER BY `p`.`id` DESC SEPARATOR "| " ), "| ", 1) as last_post_date,
IFNULL(MAX(p.date), t.date) AS pts
FROM
`topics` t
LEFT JOIN
`posts` p ON `p`.`topics_id` = `t`.`id`
LEFT JOIN
`users` u ON `u`.`id` = `t`.`user_id`
GROUP BY
`t`.`id`
ORDER BY
`pts` DESC
LIMIT 10
我在这里找到了 10 个最新主题的标题、它们的作者用户名和 ID、每个主题中的消息数量、每个主题中的最后 ID 和发帖日期,以及按事件排序的所有内容……基本上是所有内容。我所需要的只是最后一篇文章的作者用户名。我想我必须用子查询进行一个左连接,但我有点卡住了。 有人可以帮助我吗?
最佳答案
而不是形成包含整个线程帖子串联的字符串,然后从中获取第一个子字符串(按 id
排序),这不仅会拖累性能(因为它不可控制并且需要昂贵的字符串操作),但也容易出现错误(如果分隔符恰好出现在被连接的字符串中或者连接结果超出 MySQL 的限制)...
您真正想做的是获取 groupwise maximum ,可以通过将 posts
表与其上的子查询连接起来来获得。然后,您只需第二次加入 users
表(这次是针对上一篇文章)即可获取所需的用户名:
SELECT topic.id
, topic.title
, topic.date
, topic.user_id
, topic_user.username
, t.count_posts
, lastpost.id
, lastpost.date
, lastpost_user.username
, IFNULL(lastpost.date, topic.date) AS pts
FROM topics topic
LEFT JOIN users topic_user ON topic_user.id = topic.user_id
LEFT JOIN (
(
SELECT topics_id
, COUNT(*) AS count_posts
, MAX(date) AS date
FROM posts
GROUP BY topics_id
) t JOIN posts lastpost USING (topics_id, date)
LEFT JOIN users lastpost_user ON lastpost_user.id = lastpost.user_id
) ON lastpost.topics_id = topic.id
ORDER BY pts DESC
LIMIT 10
请注意,我还通过 date
而不是 id
来识别 lastpost
,因为合成 key 不应该真正用于确定自然特性;但是,这假设 date
实际上是一个时间戳。
关于mysql - 左连接最后一条记录(包含主题、最后帖子和用户的简单讨论板),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24937920/