sql語句查詢排名mysql
思路:有點相似循環裏面的自增同樣,設置一個變量並賦予初始值,循環一次自增長1,從而實現排序;sql
mysql裏則是須要先將數據查詢出來並先行按照須要排序的字段作好降序desc,或則升序asc,設置好排序的變量(初始值爲0):數據庫
a>.將已經排序好的數據從第一條依次取出來,取一條就自增長一,實現從1到最後的一個排名spa
b>.當出現相同的數據時,排名保持不變,此時則須要再設置一個變量,用來記錄上一條數據的值,跟當前數據的值進行對比,若是相同,則排名不變,不相同則排名自增長1code
c.當出現相同的數據時,排名保持不變,可是保持不變的排名依舊會佔用一個位置,也就是相似於(1,2,2,2,5)這種排名就是屬於中間的三個排名是同樣的,可是第五個排名按照上面一種狀況是(1,2,2,2,3),如今則是排名相同也會佔據排名的位置blog
準備數據(用戶id,分數):排序
CREATE TABLE `sql_rank` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`user_id` int(11) unsigned NOT NULL,
`score` tinyint(3) unsigned NOT NULL,
`add_time` date NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;class
插入數據:變量
INSERT INTO sql_rank (user_id, score, add_time)
VALUES
(100, 50, '2016-05-01'),
(101, 30, '2016-05-01'),
(102, 20, '2016-05-01'),
(103, 60, '2016-05-01'),
(104, 80, '2016-05-01'),
(105, 50, '2016-05-01'),
(106, 70, '2016-05-01'),
(107, 85, '2016-05-01'),
(108, 60, '2016-05-01')date
當前數據庫數據:
1、sql1{無論數據相同與否,排名依次排序(1,2,3,4,5,6,7.....)}
SELECT obj.user_id,obj.score,@rownum := @rownum + 1 AS rownum FROM ( SELECT user_id, score FROM `sql_rank` ORDER BY score DESC ) AS obj, (SELECT @rownum := 0) r
執行的結果以下圖:
能夠看到,如今按照分數從1到9都排好序了,可是有些分數相同的用戶排名卻不同,這就是接下來要說的第二種sql
2、sql2{只要數據有相同的排名就同樣,排名依次排序(1,2,2,3,3,4,5.....)}
SELECT obj.user_id, obj.score, CASE WHEN @rowtotal = obj.score THEN @rownum WHEN @rowtotal := obj.score THEN @rownum :=@rownum + 1 WHEN @rowtotal = 0 THEN @rownum :=@rownum + 1 END AS rownum FROM ( SELECT user_id, score FROM `sql_rank` ORDER BY score DESC ) AS obj, (SELECT @rownum := 0 ,@rowtotal := NULL) r
這時候就新增長了一個變量,用於記錄上一條數據的分數了,只要當前數據分數跟上一條數據的分數比較,相同分數的排名就不變,不相同分數的排名就加一,而且更新變量的分數值爲該條數據的分數,依次比較
以下圖結果:
跟第一條sql的結果相對比你會發現,分數相同的排名也相同,而且最後一名的名次由第9名變成了第7名;
若是你須要分數相同的排名也相同,可是後面的排名不能受到分數相同排名相同而不佔位的影響,也就是哪怕你排名相同,你也佔了這個位置(好比:1,2,2,4,5,5,7....這種形式的,雖然排名有相同,可是你佔位了,後續的排名根據佔位來排)
3、sql2{只要數據有相同的排名就同樣,可是相同排名也佔位,排名依次排序(1,2,2,4,5,5,7.....)}
此時需呀再增長一個變量,來記錄排序的號碼(自增)
SELECT obj_new.user_id, obj_new.score, obj_new.rownum FROM ( SELECT obj.user_id, obj.score, @rownum := @rownum + 1 AS num_tmp, @incrnum := CASE WHEN @rowtotal = obj.score THEN @incrnum WHEN @rowtotal := obj.score THEN @rownum END AS rownum FROM ( SELECT user_id, score FROM `sql_rank` ORDER BY score DESC ) AS obj, ( SELECT @rownum := 0 ,@rowtotal := NULL ,@incrnum := 0 ) r ) AS obj_new
上面sql執行的結果以下:
結果集中分數相同的,排名相同,同時它也佔據了那個位置,中間的一個數據過程本人截圖了,請往下看(跟上圖作對比你就明白了):
本人初學,若有發現內容錯誤,請及時評論,我好更正修改,謝謝你們!