MAX函数和GROUP BY 语句一起使用的一个误区
使用MAX 函數和 GROUP 的時候會有不可預料的數據被SELECT 出來。
下面舉個簡單的例子:
想知道每個SCOREID 的 數學成績最高的分數。
表信息:
/*DDL Information For - test.lkscore*/
--------------------------------------
Table Create Table
------- -----------------------------------------------------------------------------
lkscore CREATE TABLE `lkscore` (
`scoreid` int(11) DEFAULT NULL,
`chinese` int(11) DEFAULT '0',
`math` int(11) DEFAULT '0',
KEY `fk_class` (`scoreid`),
CONSTRAINT `fk_class` FOREIGN KEY (`scoreid`) REFERENCES `lkclass` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=gb2312
select*fromlkscore;
|
query result(12 record
| scoreid | chinese | math |
| 1 | 90 | 80 |
| 2 | 100 | 99 |
| 3 | 29 | 98 |
| 4 | 87 | 79 |
| 5 | 89 | 99 |
| 1 | 49 | 98 |
| 3 | 98 | 56 |
| 2 | 76 | 88 |
| 2 | 80 | 90 |
| 3 | 90 | 70 |
| 1 | 90 | 90 |
| 1 | 67 | 90 |
錯誤的SELECT
selectscoreid,chinese,max(math)max_mathfromlkscore group by scoreid;
|
query result(5 records)
| scoreid | chinese | max_math |
| 1 | 90 | 98 |
| 2 | 100 | 99 |
| 3 | 29 | 98 |
| 4 | 87 | 79 |
| 5 | 89 | 99 |
上面的90明顯不對。
方法一:
selectscoreid,chinese,math max_mathfrom(select*fromlkscore order by math desc)Tgroup by scoreid;
|
query result(5 records)
| scoreid | chinese | max_math |
| 1 | 49 | 98 |
| 2 | 100 | 99 |
| 3 | 29 | 98 |
| 4 | 87 | 79 |
| 5 | 89 | 99 |
方法二:
select*fromlkscore awherea.math=(selectmax(math)fromlkscorewherescoreid=a.scoreid)order by scoreid asc;
|
query result(5 records)
| scoreid | chinese | max_math |
| 1 | 49 | 98 |
| 2 | 100 | 99 |
| 3 | 29 | 98 |
| 4 | 87 | 79 |
| 5 | 89 | 99 |
這個也是用MAX函數,而且還用到了相關子查詢。
我們來看一下這兩個的效率如何:
explain
|
query result(2 records)
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
| 1 | PRIMARY | <derived2> | ALL | (NULL) | (NULL) | (NULL) | (NULL) | 12 | Using temporary; Using filesort |
| 2 | DERIVED | lkscore | ALL | (NULL) | (NULL) | (NULL) | (NULL) | 12 | Using filesort |
很明顯,有兩個FULL TABLE SCAN。
|
query result(2 records)
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
| 1 | PRIMARY | a | index | (NULL) | fk_class | 5 | (NULL) | 12 | Using where |
| 2 | DEPENDENT SUBQUERY | lkscore | ref | fk_class | fk_class | 5 | a.scoreid | 1 | Using where |
第二個就用了KEY,子查詢里只掃描了一跳記錄。
很明顯。在這種情況下第二個比第一個效率高點。
總結
以上是生活随笔為你收集整理的MAX函数和GROUP BY 语句一起使用的一个误区的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 微信支付中分账功能 填坑指南V1
- 下一篇: 数字表格