1. 程式人生 > >mysql中group by 的用法解析

mysql中group by 的用法解析

1. group by的常規用法

group by的常規用法是配合聚合函式,利用分組資訊進行統計,常見的是配合max等聚合函式篩選資料後分析,以及配合having進行篩選後過濾。

  • 假設現有資料庫表如下:
    表user_info,id主鍵,user_id唯一鍵
CREATE TABLE `user_info` (
    `id` INT(11) NOT NULL AUTO_INCREMENT COMMENT '主鍵id',
    `user_id` VARCHAR(50) NOT NULL DEFAULT '' COMMENT '使用者編號',
    `grade` VARCHAR
(50) NOT NULL DEFAULT '' COMMENT '年級', `class` VARCHAR(50) NOT NULL DEFAULT '' COMMENT '班級', PRIMARY KEY (`id`), UNIQUE INDEX `uniq_user_id` (`user_id`) ) ENGINE=InnoDB
  • 資料
INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`) VALUES (10, '10230', 'C', 'B');
INSERT INTO `user_info`
(`id`, `user_id`, `grade`, `class`) VALUES (9, '10229', 'C', 'a');
INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`) VALUES (8, '10228', 'B', 'b'); INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`) VALUES (7, '10227', 'B', 'b'); INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`
) VALUES (6, '10226', 'B', 'a');
INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`) VALUES (5, '10225', 'B', 'a'); INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`) VALUES (4, '10224', 'A', 'b'); INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`) VALUES (3, '10223', 'A', 'b'); INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`) VALUES (2, '10222', 'A', 'a'); INSERT INTO `user_info` (`id`, `user_id`, `grade`, `class`) VALUES (1, '10221', 'A', 'a');
id user_id grade class
1 10221 A a
2 10222 A a
3 10223 A b
4 10224 A b
5 10225 B a
6 10226 B a
7 10227 B b
8 10228 B b
9 10229 C a
10 10230 C b
  • 聚合函式max
select max(user_id),grade from user_info group by grade ;

結果

max(user_id) grade
10224 A
10228 B
10230 C

這條sql的含義很明確,將資料按照grade欄位分組,查詢每組最大的user_id以及當前組內容。注意,這裡分組條件是grade,查詢的非聚合條件也是grade。這裡不產生衝突。

  • having
select max(user_id),grade from user_info group by grade  having grade>'A'

結果

max(user_id) grade
10228 B
10230 C

這條sql與上面例子中的基本相同,不過後面跟了having過濾條件。將grade不滿足’>A’的過濾掉了。注意,這裡分組條件是grade,查詢的非聚合條件也是grade。這裡不產生衝突。

2. group by的非常規用法

select max(user_id),id,grade from user_info group by grade  

結果

max(user_id) id grade
10224 1 A
10228 5 B
10230 9 C

這條sql的結果就值得討論了,與上述例子不同的是,查詢條件多了id一列。資料按照grade分組後,grade一列是相同的,max(user_id)按照資料進行計算也是唯一的,id一列是如何取值的?看上述的資料結果,
推論:id是實體記憶體的第一個匹配項。
究竟是與不是需要繼續探討。

修改資料

  • 修改id按照上述資料結果,將id=1,改為id=99,執行sql後結論:
max(user_id) id grade
10224 2 A
10228 5 B
10230 9 C

顯然,與上述例子的結果不同。第一條資料id變成了99,查出的結果第一條資料的id從1變成了2。表明,id這個非聚合條件欄位的取值與資料寫入的時間無關,因為id=1的記錄是先於id=2存在的,修改的資料不過是修改了這條資料的內容。結合mysql的資料儲存理論,由於id是主鍵,所以資料在檢索是是按照主鍵排序後進行過濾的,因此
推論:id欄位的選取是按照mysql儲存的檢索資料匹配的第一條
將id改為1後恢復了原始結果,無法推翻上述推論。

  • 更改查詢條件

    select max(user_id),user_id,id,grade from user_info group by grade
max(user_id) user_id id grade
10224 10221 1 A
10228 10225 5 B
10230 10229 9 C

將資料user_id改為10999後,執行結果為

max(user_id) user_id id grade
10224 10999 1 A
10228 10225 5 B
10230 10229 9 C

修改了user_id後,並沒有改變查詢到的資料條目,因此得出修改唯一鍵並不能影響查詢匹配的條目規則,所以條目規則依然是匹配第一條,即id=1。

結論

  • 當group by 與聚合函式配合使用時,功能為分組後計算
  • 當group by 與having配合使用時,功能為分組後過濾
  • 當group by 與聚合函式,同時非聚合欄位同時使用時,非聚合欄位的取值是第一個匹配到的欄位內容,即id小的條目對應的欄位內容。

相關推薦

mysqlgroup by用法解析

1. group by的常規用法 group by的常規用法是配合聚合函式,利用分組資訊進行統計,常見的是配合max等聚合函式篩選資料後分析,以及配合having進行篩選後過濾。 假設現有資料庫表如下: 表user_info,id主鍵,user_id唯一

mysqlgroup by用法在5.7和5.6存在區別

http://stackoverflow.com/questions/39909261/order-by-before-group-by-in-subquery-working-in-mysql-5-5-but-not-in-mysql-5-7 http://stackov

mysql group by 用法解析(詳細)

group by 用法解析 group by語法可以根據給定資料列的每個成員對查詢結果進行分組統計,最終得到一個分組彙總表。 SELECT子句中的列名必須為分組列或列函式。列函式對於GROUP BY子句定義的每個組各返回一個結果。 某個員工資訊表結構和資料如下:   id 

mysqlgroup by和order by同時使用無效的替代方案

前言 最近一年由於工作需要大部分使用的都是NoSql資料庫,對關係型資料庫感覺越來越陌生,一個由group by和order by 引發的血案由此而生。在此做個記錄,以備不時之需。 需求(得到所有barCode的最新的一條資料) 首先,看一下整體的表結構。 

mysqlgroup by和order by同時使用無效 group_concat

                                          &nb

關於mysql group by , order by , where, having 語句的區別與運用

最近一直在忙著和資料庫有關的一些工作,這幾天在寫儲存過程的時候,一些mysql的語句突然感覺有些不太明白,就是group   by   ,  order   by  ,where   ,  having這些語句,這次通過一個例項來總結和歸納一下,這幾個語句的用法,僅供以後參

mysqlgroup by分組後查詢無資料補0;

mysql經常會用到Group By來進行分組查詢,但也經常會遇到一個問題,就是當有where條件時,被where條件過濾的資料不顯示了。 例如我有一組資料: 我想查詢當日領取數量和當日核銷數量;

mysqlgroup by

對於group by在mysql中的使用和Oracle的差異性很大,準確的說不光和Oracle和別的資料庫差異性一樣,這些有點不太遵循標準SQL。我們知道常規的 sql,對於group by來說一定要結合聚合函式,而且選擇的欄位除了聚合函式外,還必須在group by中出現,否則報錯,但是在mysql中擴充

MySql含有GROUP BY子句的查詢如何顯示COUNT()為0的結果

前階段工作中發現MySql含有GROUP BY子句的查詢中COUNT()為0的結果不顯示. 而針對於分組統計的此類問題,多數人(包括本人)通常會想到: SELECT PID,COUNT(1) AS SUM FROM SS WHERE FIAG = 1 GROUP BY PID

mysql group by 用法

group by 用法解析 group by語法可以根據給定資料列的每個成員對查詢結果進行分組統計,最終得到一個分組彙總表。 SELECT子句中的列名必須為分組列或列函式。列函式對於GROUP BY子句定義的每個組各返回一個結果。 某個員工資訊表結構和資料如下:   id 

mysql 5.7高版本group by問題解決辦法

select max(user_id) as user_id,`create_time` from silence where user_id in (1, 2, 3, 4) group by user_id desc; 我使用如上語句進行查詢的時候,竟然報錯了。 Expressi

mysqlorder by的一些特殊用法

公司需要查詢資料,排序的時候,需要把一部分資料放在所有資料前面,舉個例子來說,所有資料按照時間排序,有時需要將昨天的排在最前面,有時需要將前天的排在最前面,想了很久不知道從何下手,而我又不想在前端做這件事情,所以想了這麼個方法,直接上程式碼 <select id="f

SQL語句 group by 和 having 的用法

聚合函式:例如SUM, COUNT, MAX, AVG等。這些函式和其它函式的根本區別就是它們一般作用在多條記錄上。 having是分組(group by)後的篩選條件,分組後的資料組內再篩選 where則是在分組前篩選 簡單來說,group by 相當於

MySql 資料庫group by用法,order by 巢狀使用。優化問題

不多說,直接看例子。自己動手試試 mysql> select * from tb_clothes; +----+--------+-------+-------+------------+---------+ | id | name | price | tot

mybatisgroup by 語句SQL報錯,原因是MySQL版本的group規則預設是:only_full_group_by

報錯資訊:......not in GROUP BY clause and contains nonaggregated column ......  which is not functionally dependent on columns in GROUP BY cla

mysqlorder bygroup by的詳細區別是詳細區別

order by 排序查詢、asc升序、desc降序示例:select * from 學生表 order by 年齡 查詢學生表資訊、按年齡的升序(預設、可預設、從低到高)排列顯示也可以多條件排序、 比如 order by 年齡,成績 desc 按年齡升序排列後

關於mysql group by 用法總結

group by 用法 select 聚合函式(分組欄位) from table group by table.id having …… 當sql語句中包含group by 時,select後的欄位只能是聚合函式或者group by 後面的分組欄位。如果需要

mysql精粹:group by 很好的函式

在MySQL中,你可以獲取表示式組合的連線值。你可以使用DISTINCT刪去重複值。假若你希望多結果值進行排序,則應該使用  ORDER BY子句。若要按相反順序排列,將 DESC (遞減) 關鍵詞新增到你要用ORDER BY 子句進行排序的列名稱中。預設順序為升序;可使用ASC將其明確指定。   SE

mysqlorder bygroup by的順序

mysql 中order by 與group by的順序 是: select from where group by order by 注意:group by 比order by先執行,order by不會對group by 內部進行排序,如果group by後只有一條記

mysql使用GROUP BY分組實現取前N條記錄的方法

cls class ges rom 當前 分組 實現 一個 images MySQL中GROUP BY分組取前N條記錄實現 mysql分組,取記錄 GROUP BY之後如何取每組的前兩位下面我來講述mysql中GROUP BY分組取前N條記錄實現方法。 這是測試表(也