如何在mysql表中选择最大值行

时间:2013-06-26 11:09:41

标签: mysql performance

我有下表

表格结构:

CREATE TABLE IF NOT EXISTS `people` ( 
`name` varchar(10) NOT NULL, 
`age` smallint(5) unsigned NOT NULL, 
PRIMARY KEY (`name`) 
) ENGINE=InnoDB DEFAULT CHARSET=latin1; 

插入一些值:

INSERT INTO `people` (`name`, `age`) VALUES 
('bob', 13), 
('john', 25), 
('steve', 8), 
('sue', 13); 

已执行查询

SELECT MAX(  `age` ) ,  `name` FROM  `people` WHERE 1

预期结果:

25, John

生成结果

25, bob

我们可以通过使用此查询来实现此目的

SELECT `age`,  `name` FROM  `people` ORDER BY age DESC LIMIT 1

问题1:我在这里犯了什么错误,为什么这个MAX函数没有返回相关的行信息?

问题2:哪一个好用,增加性能MAX函数或ORDER BY子句?

7 个答案:

答案 0 :(得分:21)

  

问题1:我在这里弄错了为什么这个MAX函数没有返回相关的行信息?

您需要阅读group by条款。

MySQL比它应该允许的更宽松,在这个过程中引入了混乱。基本上,任何没有聚合的列都应包含在group by子句中。但MySQL语法糖允许“忘记”列。当你这样做时,MySQL会从它所分组的集合中吐出一个任意值。在您的情况下,集合中的第一行是bob,因此它返回。

  

问题2:哪一个好用,增加性能MAX函数或ORDER BY子句?

您的第一个声明(使用max()而不是group by)是完全错误的。

如果您想要最老的用户之一,order by age desc limit 1是正确的继续使用方式。

如果您想要所有最老的用户,则需要进行子选择:

SELECT p.* FROM people p WHERE p.age = (select max(subp.age) from people subp);

答案 1 :(得分:11)

试试这个

SELECT age, name FROM  `people` where age = (SELECT max(age) FROM  people)

答案 2 :(得分:8)

另一种不使用聚合函数和分组的解决方案:

SELECT * FROM people ORDER BY age DESC LIMIT 1

答案 3 :(得分:3)

  

我在这里弄错了为什么这个MAX函数没有返回相关的行信息?

MAX返回正确的值 - 但您选择的另一列只会为您提供“随机”值。

选择不属于GROUPing的列(我认为隐式GROUP BY在这里完成,因为你使用了聚合函数)在严格的SQL中是非法的 - 但MySQL忽略了它(取决于服务器配置),并给你一个在这种情况下来自“随机”行的值。


此处描述了替代方法:The Rows Holding the Group-wise Maximum of a Certain Column

答案 4 :(得分:0)

MAX是aggregate function。这意味着MySQL将所有记录分组并将它们视为结果集中的记录。由于您没有说明如何对名称列进行分组,因此结果可能是意外的。 ORDER BY是实现理想结果的完美方式。只是不要忘记在年龄上添加index,这样随着表格的增长,性能不会受到影响。

答案 5 :(得分:0)

问题1: 如果你真的想使用MAX() 你可以试试这个 SELECT age, name FROM people WHERE age IN (SELECT MAX(age) FROM people);

问题2: 我认为这取决于我在问题1中的建议,您执行了两次查询,但在您提供的ORDER BY解决方案中,数据库执行了类似过程的操作。

答案 6 :(得分:0)

有一个有趣的替代方案仅适用于MySql!

SELECT `Name`, `Age` FROM 
(SELECT `Name`, `Age`, 1 AS `foo`
FROM `People`
ORDER BY `Age` DESC) AS `x`
GROUP BY `foo`

这是有效的,因为当给定列

上没有应用聚合函数时,MySql返回第一行

以下是链接:http://tominology.blogspot.com.br/2014/10/sql-row-with-max-value.html