好的,这是我的桌子:
product_id version_id update_id patch_id
1 1 0 0
1 1 1 0
1 1 1 1
1 1 2 0
1 1 2 1
2 1 0 0
2 2 0 0
2 3 0 0
2 3 0 1
3 1 0 0
3 1 0 1
Run Code Online (Sandbox Code Playgroud)
现在我想选择产品的最新版本,因此具有最高update_id和patch_id的版本.
例如,最新版本的
我正在尝试使用GROUP BY和HAVING的各种东西,尝试了子查询,但我仍然无法找到实现这一目标的方法.
任何人都可以帮我找到正确的查询,还是应该考虑为此编写一个php函数?
编辑
一些额外的信息: - 列一起是主键(有更多列,但对于这个问题,它们无关紧要) - 没有列是自动增量
这是表:
CREATE TABLE IF NOT EXISTS `db`.`patch` (
`product_id` INT NOT NULL ,
`version_id` INT NOT NULL ,
`update_id` INT NOT NULL ,
`patch_id` INT NOT NULL
PRIMARY KEY (`product_id`, `version_id`, `update_id`, `patch_id`) ,
INDEX `fk_patch_update1` (`product_id` ASC, `version_id` ASC, `update_id` ASC) )
Run Code Online (Sandbox Code Playgroud)
编辑2
标记为重复,但不是:另一个问题查找的记录高于三个不同列中任何一列的值.
在这个问题中,我们寻找由product_id分组的最高版本号.
编辑3
rgz的回答再次告诉我,这是重复的.首先:这个问题比较老了.其次,我不认为答案是一样的.
rgz建议使用以下查询:
SELECT product_id, GREATEST(version_id, update_id, patch_id) AS latest_version FROM patch.
Run Code Online (Sandbox Code Playgroud)
GREATEST(1,2,3)返回3,对吗?Wat如果我们有这些值:
product_id version_id update_id patch_id
1 1 0 0
1 1 2 8
1 3 0 0
Run Code Online (Sandbox Code Playgroud)
据我了解,此查询将返回:
product_id latest_version
1 1
1 8
1 3
Run Code Online (Sandbox Code Playgroud)
但它应该返回:
product_id version_id update_id patch_id
1 3 0 0
Run Code Online (Sandbox Code Playgroud)
我认为GREATEST不会有所帮助.如果你认为它会,请证明我错了.
这是独特标识有用的一个例子.
想象一下,您有一个autoincrememnting ID字段,然后您可以使用相关的子查询找到每个产品所需的ID ...
SELECT
*
FROM
yourTable
WHERE
id = (
SELECT id
FROM yourTable AS lookup
WHERE lookup.product_id = yourTable.product_id
ORDER BY version_id DESC, update_id DESC, patch_id DESC
LIMIT 1
)
Run Code Online (Sandbox Code Playgroud)
没有唯一标识符的等价物需要多个相关的子查询...
SELECT
*
FROM
yourTable
WHERE
version_id = (
SELECT MAX(version_id)
FROM yourTable AS lookup
WHERE lookup.product_id = yourTable.product_id
)
AND update_id = (
SELECT MAX(update_id)
FROM yourTable AS lookup
WHERE lookup.product_id = yourTable.product_id
AND lookup.version_id = yourTable.version_id
)
AND patch_id = (
SELECT MAX(patch_id)
FROM yourTable AS lookup
WHERE lookup.product_id = yourTable.product_id
AND lookup.version_id = yourTable.version_id
AND lookup.update_id = yourTable.update_id
)
Run Code Online (Sandbox Code Playgroud)
这将明显慢于具有唯一标识符列的表.
另一种替代方案(没有唯一标识符)是在不同的聚合级别上自我加入.
SELECT
yourTable.*
FROM
(SELECT product_id, MAX(version_id) AS max_version_id FROM yourTable GROUP BY product_id) AS version
INNER JOIN
(SELECT product_id, version_id, MAX(update_id) AS max_update_id FROM yourTable GROUP BY product_id, version_id) AS update
ON update.product_id = version.product_id
AND update.version_id = version.max_version_id
INNER JOIN
(SELECT product_id, version_id, updatE_id, MAX(patch_id) AS max_patch_id FROM yourTable GROUP BY product_id, version_id) AS patch
ON patch.product_id = update.product_id
AND patch.version_id = update.version_id
AND patch.update_id = update.max_update_id
INNER JOIN
yourTable
ON yourTable.product_id = patch.product_id
AND yourTable.version_id = patch.version_id
AND yourTable.update_id = patch.update_id
AND yourTable.patch_id = patch.max_patch_id
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
16889 次 |
| 最近记录: |