我有3個非常簡單的表:複雜的SQL查詢的排名
用戶
user_id
1
2
3
radio_songs
song_id song
1 SomeName
2 OtherName
radio_rates
user_id song_id rate (from 1 to 5)
1 1 5
2 1 4
1 2 2
2 2 2
我已經寫了相當複雜的查詢打靶MySQL的那個cal culates當前「位置」的歌曲根據lower bound of Wilson score confidence interval for a Bernoulli parameter(秩)。
SELECT rank FROM(
SELECT x.song AS song, x.ci_lower_bound AS ci_lower_bound, (@row:= @row + 1) AS rank FROM(
SELECT song, ((SUM((rate - 1) * 0.25) + 1.9208)/(SUM((rate - 1) * 0.25) + SUM((5 - rate) * 0.25)) - 1.96 * SQRT((SUM((rate - 1) * 0.25) * SUM((5 - rate) * 0.25))/(SUM((rate - 1) * 0.25) + SUM((5 - rate) * 0.25)) + 0.9604)/(SUM((rate - 1) * 0.25) + SUM((5 - rate) * 0.25)))/(1 + 3.8416/(SUM((rate - 1) * 0.25) + SUM((5 - rate) * 0.25))) AS ci_lower_bound
FROM radio_rates
INNER JOIN radio_songs ON radio_rates.song_id = radio_songs.song_id
GROUP BY radio_rates.song_id
ORDER BY ci_lower_bound DESC
) x, (SELECT @row := 0) r
) xx WHERE xx.song = @song
該查詢基本上接受@song
參數:
- 計算下界威爾遜的得分以降序通過它的訂單
- 添加行號的每一行,因爲我沒有找到任何方式在MySQL
ROW_NUMBER()
最後得到這首歌的排名,我們正在尋找
該查詢正常工作,對此我非常滿意,但是當我們有多個具有相同分數的歌曲時,由於對結果排序進行排序可能會因同一SQL查詢的執行而有所不同。我想,以避免由具有相同的分數作爲目標一個所有歌曲越來越MIN()
排名,但查詢有這麼複雜,我掙扎怎麼做,沒有一個臨時表 - 它甚至可能嗎?
我會很感激的幫助,以及在上面查詢的性能/優化方面的任何建議。
我知道這將會是值得考慮只需添加另一個得分列歌曲表,計算它通過觸發器每個插入/更新,但我想避免,如果可能的和按需計算排名。因此SQL查詢本身對我來說最重要。
預先感謝您。
'RANK()'是在MySQL中實現一個痛。 'DENSE_RANK()'更簡單一些。 –