SQL LEFT JOIN问题

时间:2010-08-04 23:22:08

标签: sql mysql greatest-n-per-group

我正在尝试选择最新的updated(字段)pages(表格),不包括隐藏的页面(visible =“n”)。但是,我想按slug对页面进行分组,因此每个slug只能获得一个结果。

以下查询有点可行,但它只为每个slug选择最新更新的页面 - 然后,如果该页面恰好被隐藏,则将其从结果中删除:( 在这种情况下我只想获得 可见的那个slug的最新更新页面。

SELECT `p1`.`id` AS `pID`, `p1`.`slug` AS `url`, `p1`.`revision`, `p1`.`title`, `p1`.`published`, `p1`.`updated`, (SELECT COUNT(*) FROM `pages` WHERE `slug` = `url` AND `visible` = "y") AS `revisionCount`, (SELECT COUNT(*) FROM `tests` WHERE `pageID` = `pID`) AS `testCount`
FROM `pages` `p1`
LEFT JOIN `pages` `p2` ON `p1`.`slug` = `p2`.`slug` AND `p1`.`updated` < `p2`.`updated`
WHERE `p2`.`updated` IS NULL AND `p1`.`visible` = "y"
ORDER BY `p1`.`updated` DESC

2 个答案:

答案 0 :(得分:2)

这是GROUP BY的经典案例。因为在您的情况下,您甚至不希望页面被视为,除非它是“可见的”,您将使用WHERE子句而不是HAVING子句。

SELECT MAX(id) as highest_id_for_slug, slug
FROM pages
GROUP BY slug 
WHERE visible = 'y'

如果要将这些ID连接到pages表,或者添加其他字段,可以在子查询中使用它 - 只需记住SELECT列表中的每一列必须在GROUP BY中的规则,或者具有聚合适用于它。

SELECT * FROM pages WHERE pages.id IN (
  SELECT MAX(id) as highest_id_for_slug
  FROM pages
  GROUP BY slug 
  WHERE visible = 'y'
)

答案 1 :(得分:1)

这应该有效:

SELECT id AS pID, slug AS url, revision, title, published, updated, (SELECT COUNT(*) FROM pages WHERE slug = url AND visible = "y") AS revisionCount, (SELECT COUNT(*) FROM tests WHERE pageID = pID) AS testCount
FROM pages
WHERE updated IN (SELECT MAX(updated) FROM pages WHERE visible = "y" GROUP BY slug) AND visible = "y"
ORDER BY updated DESC

P.S。所有的反叛都有什么用?